summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--android/app/res/values-af/strings.xml6
-rw-r--r--android/app/res/values-bs/strings.xml2
-rw-r--r--android/app/res/values-gu/strings.xml2
-rw-r--r--android/app/res/values-hr/strings.xml2
-rw-r--r--android/app/res/values-kn/strings_pbap.xml2
-rw-r--r--android/app/res/values-sq/strings.xml4
-rw-r--r--android/app/src/com/android/bluetooth/BluetoothMethodProxy.java11
-rw-r--r--android/app/src/com/android/bluetooth/btservice/AdapterService.java8
-rw-r--r--android/app/src/com/android/bluetooth/opp/BluetoothOppLauncherActivity.java81
-rw-r--r--android/app/tests/unit/src/com/android/bluetooth/opp/BluetoothOppLauncherActivityTest.java245
-rw-r--r--flags/security.aconfig81
-rw-r--r--framework/java/android/bluetooth/BluetoothLeAudioCodecConfigMetadata.java15
-rw-r--r--framework/java/android/bluetooth/BluetoothLeAudioContentMetadata.java5
-rw-r--r--framework/java/android/bluetooth/BluetoothLeBroadcastReceiveState.java19
-rw-r--r--framework/java/android/bluetooth/BluetoothLeBroadcastSettings.java17
-rw-r--r--system/btif/src/btif_dm.cc26
-rw-r--r--system/main/shim/le_scanning_manager.cc12
-rw-r--r--system/stack/avct/avct_lcb_act.cc5
-rw-r--r--system/stack/avdt/avdt_msg.cc10
-rw-r--r--system/stack/bnep/bnep_main.cc4
-rw-r--r--system/stack/bnep/bnep_utils.cc3
-rw-r--r--system/stack/btm/btm_sec.cc19
-rw-r--r--system/stack/hid/hidd_conn.cc4
-rw-r--r--system/stack/rfcomm/rfc_ts_frames.cc3
-rw-r--r--system/stack/rfcomm/rfc_utils.cc3
-rw-r--r--system/stack/sdp/sdp_discovery.cc6
-rw-r--r--system/stack/sdp/sdp_server.cc6
-rw-r--r--system/stack/smp/smp_act.cc12
28 files changed, 535 insertions, 78 deletions
diff --git a/android/app/res/values-af/strings.xml b/android/app/res/values-af/strings.xml
index 6640182e24..1351675302 100644
--- a/android/app/res/values-af/strings.xml
+++ b/android/app/res/values-af/strings.xml
@@ -18,9 +18,9 @@
xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
<string name="app_name" msgid="2326164424236203271">"Bluetooth"</string>
<string name="permlab_bluetoothShareManager" msgid="5297865456717871041">"Maak toegang aflaaibestuurder oop."</string>
- <string name="permdesc_bluetoothShareManager" msgid="1588034776955941477">"Gee aan die program toegang tot die BluetoothShare-bestuurder en om dit te gebruik om lêers oor te dra."</string>
+ <string name="permdesc_bluetoothShareManager" msgid="1588034776955941477">"Gee aan die app toegang tot die BluetoothShare-bestuurder en om dit te gebruik om lêers oor te dra."</string>
<string name="permlab_bluetoothAcceptlist" msgid="5785922051395856524">"Voeg Bluetooth-toesteltoegang by aanvaarlys."</string>
- <string name="permdesc_bluetoothAcceptlist" msgid="259308920158011885">"Laat die program toe om \'n Bluetooth-toestel tydelik by aanvaarlys te voeg, sodat daardie toestel lêers na hierdie toestel kan stuur sonder die gebruiker se bevestiging."</string>
+ <string name="permdesc_bluetoothAcceptlist" msgid="259308920158011885">"Laat die app toe om \'n Bluetooth-toestel tydelik by aanvaarlys te voeg, sodat daardie toestel lêers na hierdie toestel kan stuur sonder die gebruiker se bevestiging."</string>
<string name="bt_share_picker_label" msgid="7464438494743777696">"Bluetooth"</string>
<string name="unknown_device" msgid="2317679521750821654">"Onbekende toestel"</string>
<string name="unknownNumber" msgid="1245183329830158661">"Onbekend"</string>
@@ -71,7 +71,7 @@
<string name="upload_fail_cancel" msgid="1632528037932779727">"Maak toe"</string>
<string name="bt_error_btn_ok" msgid="2802751202009957372">"OK"</string>
<string name="unknown_file" msgid="3719981572107052685">"Onbekende lêer"</string>
- <string name="unknown_file_desc" msgid="9185609398960437760">"Daar is geen program om hierdie tipe lêer te hanteer nie. \n"</string>
+ <string name="unknown_file_desc" msgid="9185609398960437760">"Daar is geen app om hierdie tipe lêer te hanteer nie. \n"</string>
<string name="not_exist_file" msgid="5097565588949092486">"Geen lêers nie"</string>
<string name="not_exist_file_desc" msgid="250802392160941265">"Die lêer bestaan nie. \n"</string>
<string name="enabling_progress_title" msgid="5262637688863903594">"Wag asseblief…"</string>
diff --git a/android/app/res/values-bs/strings.xml b/android/app/res/values-bs/strings.xml
index cd9f65c929..c446c1be27 100644
--- a/android/app/res/values-bs/strings.xml
+++ b/android/app/res/values-bs/strings.xml
@@ -115,7 +115,7 @@
<string name="bluetooth_a2dp_sink_queue_name" msgid="7521243473328258997">"Trenutno se reproducira"</string>
<string name="bluetooth_map_settings_app_icon" msgid="3501432663809664982">"Ikona aplikacije"</string>
<string name="bluetooth_disconnected" msgid="6841396291728343534">"Bluetooth audio je isključen"</string>
- <string name="a2dp_sink_mbs_label" msgid="6035366346569127155">"Bluetooth Audio"</string>
+ <string name="a2dp_sink_mbs_label" msgid="6035366346569127155">"Bluetooth zvuk"</string>
<string name="bluetooth_opp_file_limit_exceeded" msgid="6612109860149473930">"Nije moguće prenijeti fajlove veće od 4 GB"</string>
<string name="bluetooth_connect_action" msgid="2319449093046720209">"Poveži se s Bluetoothom"</string>
<string name="bluetooth_enabled_apm_title" msgid="6914461147844949044">"Bluetooth je uključen u načinu rada u avionu"</string>
diff --git a/android/app/res/values-gu/strings.xml b/android/app/res/values-gu/strings.xml
index bae6c11943..a72b635790 100644
--- a/android/app/res/values-gu/strings.xml
+++ b/android/app/res/values-gu/strings.xml
@@ -115,7 +115,7 @@
<string name="bluetooth_a2dp_sink_queue_name" msgid="7521243473328258997">"હમણાં વાગી રહ્યું છે"</string>
<string name="bluetooth_map_settings_app_icon" msgid="3501432663809664982">"ઍપ્લિકેશન આયકન"</string>
<string name="bluetooth_disconnected" msgid="6841396291728343534">"બ્લૂટૂથ ઑડિઓ ડિસ્કનેક્ટ થયું"</string>
- <string name="a2dp_sink_mbs_label" msgid="6035366346569127155">"બ્લૂટૂથ ઑડિઓ"</string>
+ <string name="a2dp_sink_mbs_label" msgid="6035366346569127155">"બ્લૂટૂથ ઑડિયો"</string>
<string name="bluetooth_opp_file_limit_exceeded" msgid="6612109860149473930">"4GB કરતા મોટી ફાઇલ ટ્રાન્સફર કરી શકાતી નથી"</string>
<string name="bluetooth_connect_action" msgid="2319449093046720209">"બ્લૂટૂથ સાથે કનેક્ટ કરો"</string>
<string name="bluetooth_enabled_apm_title" msgid="6914461147844949044">"એરપ્લેન મોડમાં બ્લૂટૂથ ચાલુ છે"</string>
diff --git a/android/app/res/values-hr/strings.xml b/android/app/res/values-hr/strings.xml
index 0931f34d13..244cda77cb 100644
--- a/android/app/res/values-hr/strings.xml
+++ b/android/app/res/values-hr/strings.xml
@@ -115,7 +115,7 @@
<string name="bluetooth_a2dp_sink_queue_name" msgid="7521243473328258997">"Upravo svira"</string>
<string name="bluetooth_map_settings_app_icon" msgid="3501432663809664982">"Ikona aplikacije"</string>
<string name="bluetooth_disconnected" msgid="6841396291728343534">"Veza Bluetooth Audija prekinuta"</string>
- <string name="a2dp_sink_mbs_label" msgid="6035366346569127155">"Bluetooth Audio"</string>
+ <string name="a2dp_sink_mbs_label" msgid="6035366346569127155">"Bluetooth zvuk"</string>
<string name="bluetooth_opp_file_limit_exceeded" msgid="6612109860149473930">"Datoteke veće od 4 GB ne mogu se prenijeti"</string>
<string name="bluetooth_connect_action" msgid="2319449093046720209">"Povezivanje s Bluetoothom"</string>
<string name="bluetooth_enabled_apm_title" msgid="6914461147844949044">"Bluetooth je uključen u načinu rada u zrakoplovu"</string>
diff --git a/android/app/res/values-kn/strings_pbap.xml b/android/app/res/values-kn/strings_pbap.xml
index 93543c990a..dee248c4e5 100644
--- a/android/app/res/values-kn/strings_pbap.xml
+++ b/android/app/res/values-kn/strings_pbap.xml
@@ -4,7 +4,7 @@
<string name="pbap_session_key_dialog_title" msgid="5103201901254778256">"%1$s ಗಾಗಿ ಸೆಶನ್‌ ಕೀ ಟೈಪ್ ಮಾಡಿ"</string>
<string name="pbap_session_key_dialog_header" msgid="5073165544713355581">"ಬ್ಲೂಟೂತ್‌ ಸೆಶನ್‌ ಕೀ ಅಗತ್ಯವಿದೆ"</string>
<string name="pbap_acceptance_timeout_message" msgid="3071798915563151284">"%1$s ರೊಂದಿಗೆ ಸಂಪರ್ಕವನ್ನು ಸ್ವೀಕರಿಸುವಲ್ಲಿ ಸಮಯ ಮುಕ್ತಾಯಗೊಂಡಿದೆ"</string>
- <string name="pbap_authentication_timeout_message" msgid="2089914949828656737">"%1$s ರೊಂದಿಗೆ ಸೆಶನ್‌ ಕೀಯನ್ನು ಇನ್‌ಪುಟ್‌ ಮಾಡುವಲ್ಲಿ ಸಮಯ ಮುಕ್ತಾಯಗೊಂಡಿದೆ"</string>
+ <string name="pbap_authentication_timeout_message" msgid="2089914949828656737">"%1$s ರೊಂದಿಗೆ ಸೆಶನ್‌ ಕೀಯನ್ನು ಇನ್‌ಪುಟ್‌ ಮಾಡುವಾಗ ಸಮಯ ಮುಕ್ತಾಯಗೊಂಡಿದೆ"</string>
<string name="auth_notif_ticker" msgid="7344125635314034621">"Obex ದೃಢೀಕರಣ ವಿನಂತಿ"</string>
<string name="auth_notif_title" msgid="6639277119990416473">"ಸೆಶನ್‌ ಕೀ"</string>
<string name="auth_notif_message" msgid="7044369885874418693">"%1$s ಗಾಗಿ ಸೆಶನ್‌ ಕೀ ಟೈಪ್ ಮಾಡಿ"</string>
diff --git a/android/app/res/values-sq/strings.xml b/android/app/res/values-sq/strings.xml
index 5b2d8f1fcf..e23003f021 100644
--- a/android/app/res/values-sq/strings.xml
+++ b/android/app/res/values-sq/strings.xml
@@ -114,8 +114,8 @@
<string name="transfer_clear_dlg_title" msgid="128904516163257225">"Pastro"</string>
<string name="bluetooth_a2dp_sink_queue_name" msgid="7521243473328258997">"Po luhet tani"</string>
<string name="bluetooth_map_settings_app_icon" msgid="3501432663809664982">"Ikona e aplikacionit"</string>
- <string name="bluetooth_disconnected" msgid="6841396291728343534">"Audioja e Bluetooth-it e shkëputur"</string>
- <string name="a2dp_sink_mbs_label" msgid="6035366346569127155">"Audioja e Bluetooth-it"</string>
+ <string name="bluetooth_disconnected" msgid="6841396291728343534">"Audioja me Bluetooth e shkëputur"</string>
+ <string name="a2dp_sink_mbs_label" msgid="6035366346569127155">"Audioja me Bluetooth"</string>
<string name="bluetooth_opp_file_limit_exceeded" msgid="6612109860149473930">"Skedarët më të mëdhenj se 4 GB nuk mund të transferohen"</string>
<string name="bluetooth_connect_action" msgid="2319449093046720209">"Lidhu me Bluetooth"</string>
<string name="bluetooth_enabled_apm_title" msgid="6914461147844949044">"Bluetooth-i aktiv në modalitetin e aeroplanit"</string>
diff --git a/android/app/src/com/android/bluetooth/BluetoothMethodProxy.java b/android/app/src/com/android/bluetooth/BluetoothMethodProxy.java
index e73c4f99ba..fe2aaa2be2 100644
--- a/android/app/src/com/android/bluetooth/BluetoothMethodProxy.java
+++ b/android/app/src/com/android/bluetooth/BluetoothMethodProxy.java
@@ -18,6 +18,7 @@ package com.android.bluetooth;
import android.annotation.NonNull;
import android.annotation.SuppressLint;
+import android.app.ComponentCaller;
import android.bluetooth.BluetoothAdapter;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.le.PeriodicAdvertisingCallback;
@@ -33,6 +34,7 @@ import android.database.Cursor;
import android.media.session.MediaController;
import android.media.session.MediaSessionManager;
import android.net.Uri;
+import android.os.Build;
import android.os.Bundle;
import android.os.CancellationSignal;
import android.os.Handler;
@@ -43,6 +45,8 @@ import android.os.ParcelFileDescriptor;
import android.provider.Telephony;
import android.util.Log;
+import androidx.annotation.RequiresApi;
+
import com.android.bluetooth.bass_client.BassClientPeriodicAdvertisingManager;
import com.android.internal.annotations.VisibleForTesting;
import com.android.obex.HeaderSet;
@@ -294,4 +298,11 @@ public class BluetoothMethodProxy {
MediaSessionManager manager) {
return manager.getActiveSessions(null);
}
+
+ /** Proxies {@link ComponentCaller#checkContentUriPermission(Uri, int)}. } */
+ @RequiresApi(Build.VERSION_CODES.VANILLA_ICE_CREAM)
+ public int componentCallerCheckContentUriPermission(
+ ComponentCaller caller, Uri uri, int modeFlags) {
+ return caller.checkContentUriPermission(uri, modeFlags);
+ }
}
diff --git a/android/app/src/com/android/bluetooth/btservice/AdapterService.java b/android/app/src/com/android/bluetooth/btservice/AdapterService.java
index fe9cca3409..6bba10f0da 100644
--- a/android/app/src/com/android/bluetooth/btservice/AdapterService.java
+++ b/android/app/src/com/android/bluetooth/btservice/AdapterService.java
@@ -27,6 +27,7 @@ import static android.bluetooth.BluetoothAdapter.SCAN_MODE_CONNECTABLE;
import static android.bluetooth.BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE;
import static android.bluetooth.BluetoothAdapter.SCAN_MODE_NONE;
import static android.bluetooth.BluetoothDevice.BATTERY_LEVEL_UNKNOWN;
+import static android.bluetooth.BluetoothDevice.BOND_NONE;
import static android.bluetooth.BluetoothDevice.TRANSPORT_AUTO;
import static android.bluetooth.IBluetoothLeAudio.LE_AUDIO_GROUP_ID_INVALID;
import static android.text.format.DateUtils.MINUTE_IN_MILLIS;
@@ -6321,6 +6322,13 @@ public class AdapterService extends Service {
mCsipSetCoordinatorService.handleBondStateChanged(device, fromState, toState);
}
mDatabaseManager.handleBondStateChanged(device, fromState, toState);
+
+ if (toState == BOND_NONE) {
+ // Remove the permissions for unbonded devices
+ setMessageAccessPermission(device, BluetoothDevice.ACCESS_UNKNOWN);
+ setPhonebookAccessPermission(device, BluetoothDevice.ACCESS_UNKNOWN);
+ setSimAccessPermission(device, BluetoothDevice.ACCESS_UNKNOWN);
+ }
}
static int convertScanModeToHal(int mode) {
diff --git a/android/app/src/com/android/bluetooth/opp/BluetoothOppLauncherActivity.java b/android/app/src/com/android/bluetooth/opp/BluetoothOppLauncherActivity.java
index 002ac61e97..216c0f3506 100644
--- a/android/app/src/com/android/bluetooth/opp/BluetoothOppLauncherActivity.java
+++ b/android/app/src/com/android/bluetooth/opp/BluetoothOppLauncherActivity.java
@@ -34,6 +34,9 @@ package com.android.bluetooth.opp;
import static android.view.WindowManager.LayoutParams.SYSTEM_FLAG_HIDE_NON_SYSTEM_OVERLAY_WINDOWS;
+import static java.util.function.Predicate.not;
+import static java.util.stream.Collectors.toList;
+
import android.annotation.SuppressLint;
import android.app.Activity;
import android.bluetooth.BluetoothDevicePicker;
@@ -42,25 +45,32 @@ import android.bluetooth.BluetoothProtoEnums;
import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
+import android.content.pm.PackageManager;
import android.net.Uri;
+import android.os.Build;
import android.os.Bundle;
import android.provider.Settings;
import android.util.Log;
import android.util.Patterns;
import android.widget.Toast;
+import androidx.annotation.RequiresApi;
+
import com.android.bluetooth.BluetoothMethodProxy;
import com.android.bluetooth.BluetoothStatsLog;
import com.android.bluetooth.R;
import com.android.bluetooth.Utils;
import com.android.bluetooth.content_profiles.ContentProfileErrorReportUtils;
+import com.android.bluetooth.flags.Flags;
import com.android.internal.annotations.VisibleForTesting;
+import com.android.modules.utils.build.SdkLevel;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.util.ArrayList;
+import java.util.List;
import java.util.Locale;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
@@ -124,6 +134,16 @@ public class BluetoothOppLauncherActivity extends Activity {
// Browser, share one link goes to this case;
if (stream != null && type != null) {
Log.v(TAG, "Get ACTION_SEND intent: Uri = " + stream + "; mimetype = " + type);
+ if (Flags.oppCheckContentUriPermissions() && SdkLevel.isAtLeastV()) {
+ if (!checkCallerAndSelfContentUriPermission(stream)) {
+ finish();
+ return;
+ } else {
+ Log.v(TAG, "Sender has permissions to access Uri = " + stream);
+ }
+ } else {
+ Log.v(TAG, "Did not check sender permissions to Uri = " + stream);
+ }
// Save type/stream, will be used when adding transfer
// session to DB.
Thread t =
@@ -191,6 +211,7 @@ public class BluetoothOppLauncherActivity extends Activity {
} else if (action.equals(Intent.ACTION_SEND_MULTIPLE)) {
final String mimeType = intent.getType();
final ArrayList<Uri> uris = intent.getParcelableArrayListExtra(Intent.EXTRA_STREAM);
+ final List<Uri> permittedUris;
if (mimeType != null && uris != null) {
Log.v(
TAG,
@@ -198,6 +219,37 @@ public class BluetoothOppLauncherActivity extends Activity {
+ uris
+ "\n Type= "
+ mimeType);
+ if (Flags.oppCheckContentUriPermissions() && SdkLevel.isAtLeastV()) {
+ permittedUris =
+ uris.stream()
+ .filter(this::checkCallerAndSelfContentUriPermission)
+ .collect(toList());
+ if (permittedUris.isEmpty()) {
+ Log.w(TAG, "Sender has no permissions to access any uris in " + uris);
+ finish();
+ return;
+ } else if (!permittedUris.equals(uris)) {
+ List<Uri> blockedUris =
+ uris.stream()
+ .filter(not(permittedUris::contains))
+ .collect(toList());
+ Log.w(
+ TAG,
+ "Sender has partial permissions to uris. "
+ + "Permitted uris: "
+ + permittedUris
+ + ", "
+ + "Blocked uris: "
+ + blockedUris
+ + ". "
+ + "Proceeding only with permitted uris.");
+ } else {
+ Log.v(TAG, "Sender has permissions to all uris in " + uris);
+ }
+ } else {
+ permittedUris = uris;
+ Log.v(TAG, "Did not check sender permissions to uris in " + uris);
+ }
Thread t =
new Thread(
new Runnable() {
@@ -208,7 +260,7 @@ public class BluetoothOppLauncherActivity extends Activity {
BluetoothOppLauncherActivity.this)
.saveSendingFileInfo(
mimeType,
- uris,
+ permittedUris,
false /* isHandover */,
true /* fromExternal */);
// Done getting file info..Launch device picker
@@ -291,6 +343,33 @@ public class BluetoothOppLauncherActivity extends Activity {
}
}
+ /**
+ * Checks whether the sender (and Bluetooth) have permissions to access the given content uri.
+ * The result does not differentiate the sender vs. Bluetooth's lack of permissions.
+ *
+ * @param uri A uri with a <tt>content</tt> scheme.
+ * @return true if both the sender and Bluetooth have permissions, false otherwise.
+ */
+ @RequiresApi(Build.VERSION_CODES.VANILLA_ICE_CREAM)
+ private boolean checkCallerAndSelfContentUriPermission(Uri uri) {
+ boolean hasPermission = false;
+ try {
+ hasPermission =
+ BluetoothMethodProxy.getInstance()
+ .componentCallerCheckContentUriPermission(
+ getInitialCaller(),
+ uri,
+ Intent.FLAG_GRANT_READ_URI_PERMISSION)
+ == PackageManager.PERMISSION_GRANTED;
+ } catch (SecurityException e) {
+ Log.w(TAG, "Bluetooth does not have permissions to Uri = " + uri, e);
+ }
+ if (!hasPermission) {
+ Log.w(TAG, "Sender does not have permissions to Uri = " + uri);
+ }
+ return hasPermission;
+ }
+
/* Returns true if Bluetooth is allowed given current airplane mode settings. */
private boolean isBluetoothAllowed() {
final ContentResolver resolver = this.getContentResolver();
diff --git a/android/app/tests/unit/src/com/android/bluetooth/opp/BluetoothOppLauncherActivityTest.java b/android/app/tests/unit/src/com/android/bluetooth/opp/BluetoothOppLauncherActivityTest.java
index c162cc9562..bceff44b7a 100644
--- a/android/app/tests/unit/src/com/android/bluetooth/opp/BluetoothOppLauncherActivityTest.java
+++ b/android/app/tests/unit/src/com/android/bluetooth/opp/BluetoothOppLauncherActivityTest.java
@@ -23,9 +23,14 @@ import static androidx.test.espresso.intent.matcher.IntentMatchers.hasComponent;
import static com.google.common.truth.Truth.assertThat;
+import static org.junit.Assume.assumeTrue;
import static org.mockito.ArgumentMatchers.any;
+import static org.mockito.ArgumentMatchers.anyBoolean;
+import static org.mockito.ArgumentMatchers.anyInt;
+import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.doThrow;
+import static org.mockito.Mockito.never;
import static org.mockito.Mockito.spy;
import static org.mockito.Mockito.verify;
@@ -33,7 +38,11 @@ import android.bluetooth.BluetoothDevicePicker;
import android.content.Context;
import android.content.ContextWrapper;
import android.content.Intent;
+import android.content.pm.PackageManager;
import android.net.Uri;
+import android.platform.test.annotations.DisableFlags;
+import android.platform.test.annotations.EnableFlags;
+import android.platform.test.flag.junit.SetFlagsRule;
import android.sysprop.BluetoothProperties;
import androidx.lifecycle.Lifecycle;
@@ -45,9 +54,9 @@ import androidx.test.runner.AndroidJUnit4;
import com.android.bluetooth.BluetoothMethodProxy;
import com.android.bluetooth.TestUtils;
+import com.android.bluetooth.flags.Flags;
import org.junit.After;
-import org.junit.Assume;
import org.junit.Before;
import org.junit.Ignore;
import org.junit.Rule;
@@ -59,15 +68,20 @@ import org.mockito.junit.MockitoJUnit;
import org.mockito.junit.MockitoRule;
import java.io.File;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
@MediumTest
@RunWith(AndroidJUnit4.class)
public class BluetoothOppLauncherActivityTest {
+ public static final String CONTENT_TYPE = "image/png";
+
Context mTargetContext;
Intent mIntent;
BluetoothMethodProxy mMethodProxy;
- @Rule public MockitoRule mockitoRule = MockitoJUnit.rule();
+ @Rule public MockitoRule mMockitoRule = MockitoJUnit.rule();
@Mock BluetoothOppManager mBluetoothOppManager;
@@ -76,9 +90,11 @@ public class BluetoothOppLauncherActivityTest {
// Add retry rule to resolve this problem.
@Rule public TestUtils.RetryTestRule mRetryTestRule = new TestUtils.RetryTestRule();
+ @Rule public SetFlagsRule.ClassRule mSetFlagsClassRule = new SetFlagsRule.ClassRule();
+
@Before
public void setUp() throws Exception {
- Assume.assumeTrue(BluetoothProperties.isProfileOppEnabled().orElse(false));
+ assumeTrue(BluetoothProperties.isProfileOppEnabled().orElse(false));
mTargetContext = spy(new ContextWrapper(ApplicationProvider.getApplicationContext()));
mMethodProxy = spy(BluetoothMethodProxy.getInstance());
@@ -129,6 +145,229 @@ public class BluetoothOppLauncherActivityTest {
}
@Test
+ @EnableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSend_checkEnabled_noPermission_doesNotSaveFileInfo()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_DENIED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ String uriString = "content://test.provider/1";
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendIntent(uriString));
+
+ verify(mBluetoothOppManager, never())
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriString),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ @Test
+ @EnableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSend_checkEnabled_hasPermission_savesFileInfo()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_GRANTED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ String uriString = "content://test.provider/1";
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendIntent(uriString));
+
+ verify(mBluetoothOppManager)
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriString),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ @Test
+ @DisableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSend_checkNotEnabled_noPermission_savesFileInfo()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_DENIED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ String uriString = "content://test.provider/1";
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendIntent(uriString));
+
+ verify(mBluetoothOppManager)
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriString),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ @Test
+ @DisableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSend_checkNotEnabled_hasPermission_savesFileInfo()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_GRANTED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ String uriString = "content://test.provider/1";
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendIntent(uriString));
+
+ verify(mBluetoothOppManager)
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriString),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ private Intent createSendIntent(String uriString) {
+ return new Intent(Intent.ACTION_SEND)
+ .setClass(mTargetContext, BluetoothOppLauncherActivity.class)
+ .setType(CONTENT_TYPE)
+ .putExtra(Intent.EXTRA_STREAM, Uri.parse(uriString));
+ }
+
+ @Test
+ @EnableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSendMultiple_checkEnabled_noPermission_doesNotSaveFileInfos()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_DENIED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ List<Uri> uriList =
+ Arrays.asList(
+ Uri.parse("content://test.provider/1"),
+ Uri.parse("content://test.provider/2"));
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendMultipleIntent(uriList));
+
+ verify(mBluetoothOppManager, never())
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriList),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ @Test
+ @EnableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSendMultiple_checkEnabled_hasPermission_savesFileInfos()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_GRANTED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ List<Uri> uriList =
+ Arrays.asList(
+ Uri.parse("content://test.provider/1"),
+ Uri.parse("content://test.provider/2"));
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendMultipleIntent(uriList));
+
+ verify(mBluetoothOppManager)
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriList),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ @Test
+ @EnableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void
+ onCreate_withActionSendMultiple_checkEnabled_partialPermission_savesPermittedFileInfo()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_GRANTED, PackageManager.PERMISSION_DENIED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ List<Uri> uriList =
+ Arrays.asList(
+ Uri.parse("content://test.provider/1"),
+ Uri.parse("content://test.provider/2"));
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendMultipleIntent(uriList));
+
+ verify(mBluetoothOppManager)
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(Arrays.asList(Uri.parse("content://test.provider/1"))),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ @Test
+ @DisableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSendMultiple_checkNotEnabled_noPermission_savesFileInfos()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_DENIED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ List<Uri> uriList =
+ Arrays.asList(
+ Uri.parse("content://test.provider/1"),
+ Uri.parse("content://test.provider/2"));
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendMultipleIntent(uriList));
+
+ verify(mBluetoothOppManager)
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriList),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ @Test
+ @DisableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSendMultiple_checkNotEnabled_hasPermission_savesFileInfos()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_GRANTED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ List<Uri> uriList =
+ Arrays.asList(
+ Uri.parse("content://test.provider/1"),
+ Uri.parse("content://test.provider/2"));
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendMultipleIntent(uriList));
+
+ verify(mBluetoothOppManager)
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriList),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ @Test
+ @DisableFlags(Flags.FLAG_OPP_CHECK_CONTENT_URI_PERMISSIONS)
+ public void onCreate_withActionSendMultiple_checkNotEnabled_partialPermission_savesFileInfos()
+ throws Exception {
+ doReturn(true).when(mMethodProxy).bluetoothAdapterIsEnabled(any());
+ doReturn(PackageManager.PERMISSION_GRANTED, PackageManager.PERMISSION_DENIED)
+ .when(mMethodProxy)
+ .componentCallerCheckContentUriPermission(any(), any(), anyInt());
+ List<Uri> uriList =
+ Arrays.asList(
+ Uri.parse("content://test.provider/1"),
+ Uri.parse("content://test.provider/2"));
+
+ ActivityScenario<BluetoothOppLauncherActivity> unused =
+ ActivityScenario.launch(createSendMultipleIntent(uriList));
+
+ verify(mBluetoothOppManager)
+ .saveSendingFileInfo(
+ eq(CONTENT_TYPE), eq(uriList),
+ anyBoolean() /* isHandover */, anyBoolean() /* fromExternal */);
+ }
+
+ private Intent createSendMultipleIntent(List<Uri> uriList) {
+ return new Intent(Intent.ACTION_SEND_MULTIPLE)
+ .setClass(mTargetContext, BluetoothOppLauncherActivity.class)
+ .setType(CONTENT_TYPE)
+ .putParcelableArrayListExtra(Intent.EXTRA_STREAM, new ArrayList<>(uriList));
+ }
+
+ @Test
public void onCreate_withActionOpen_sendBroadcast() throws Exception {
mIntent.setAction(Constants.ACTION_OPEN);
mIntent.setData(Uri.EMPTY);
diff --git a/flags/security.aconfig b/flags/security.aconfig
index ddfd78611c..dc6fea1ac5 100644
--- a/flags/security.aconfig
+++ b/flags/security.aconfig
@@ -44,3 +44,84 @@ flag {
purpose: PURPOSE_BUGFIX
}
}
+
+flag {
+ name: "btsec_avdt_msg_ind_type_confusion"
+ namespace: "bluetooth"
+ description: "Properly check current state and sig value of avdt rej/rsp messages before parsing"
+ bug: "358212054"
+ metadata {
+ purpose: PURPOSE_BUGFIX
+ }
+}
+
+flag {
+ name: "btsec_cycle_irks"
+ namespace: "bluetooth"
+ description: "Change the IRK per BT spec when all devices are unbonded"
+ bug: "372714979"
+ metadata {
+ purpose: PURPOSE_BUGFIX
+ }
+}
+
+flag {
+ name: "btsec_le_oob_pairing"
+ namespace: "bluetooth"
+ description: "Drop connection if a peer claims it has OOB data but no local OOB data is stored"
+ bug: "374376990"
+ metadata {
+ purpose: PURPOSE_BUGFIX
+ }
+}
+
+
+flag {
+ name: "opp_check_content_uri_permissions"
+ namespace: "bluetooth"
+ description: "Check that the launching application for OPP has read access to the given content URI, on Android V+"
+ bug: "375466974"
+ metadata {
+ purpose: PURPOSE_BUGFIX
+ }
+}
+
+flag {
+ name: "sec_disconnect_on_le_key_missing"
+ namespace: "bluetooth"
+ description: "Disconnect LE link when keys are missing during encryption"
+ bug: "376680866"
+ metadata {
+ purpose: PURPOSE_BUGFIX
+ }
+}
+
+flag {
+ name: "guard_bonded_device_properties"
+ namespace: "bluetooth"
+ description: "Don't update device properties for bonded devices from the device discovery results"
+ bug: "376928594"
+ metadata {
+ purpose: PURPOSE_BUGFIX
+ }
+}
+
+flag {
+ name: "disconnect_on_encryption_failure"
+ namespace: "bluetooth"
+ description: "Disconnect ACL link when encryption fails"
+ bug: "378764380"
+ metadata {
+ purpose: PURPOSE_BUGFIX
+ }
+}
+
+flag {
+ name: "upgrade_temp_bonding_on_auth_req"
+ namespace: "bluetooth"
+ description: "Upgrade security If it is on temp bonding & authentication is requirement"
+ bug: "385747513"
+ metadata {
+ purpose: PURPOSE_BUGFIX
+ }
+}
diff --git a/framework/java/android/bluetooth/BluetoothLeAudioCodecConfigMetadata.java b/framework/java/android/bluetooth/BluetoothLeAudioCodecConfigMetadata.java
index c48ca4c842..7beb1da111 100644
--- a/framework/java/android/bluetooth/BluetoothLeAudioCodecConfigMetadata.java
+++ b/framework/java/android/bluetooth/BluetoothLeAudioCodecConfigMetadata.java
@@ -227,12 +227,7 @@ public final class BluetoothLeAudioCodecConfigMetadata implements Parcelable {
@Override
public void writeToParcel(Parcel out, int flags) {
out.writeLong(mAudioLocation);
- if (mRawMetadata != null) {
- out.writeInt(mRawMetadata.length);
- out.writeByteArray(mRawMetadata);
- } else {
- out.writeInt(-1);
- }
+ out.writeByteArray(mRawMetadata);
out.writeInt(mSampleRate);
out.writeInt(mFrameDuration);
out.writeInt(mOctetsPerFrame);
@@ -250,12 +245,8 @@ public final class BluetoothLeAudioCodecConfigMetadata implements Parcelable {
public @NonNull BluetoothLeAudioCodecConfigMetadata createFromParcel(
@NonNull Parcel in) {
long audioLocation = in.readLong();
- int rawMetadataLen = in.readInt();
- byte[] rawMetadata;
- if (rawMetadataLen != -1) {
- rawMetadata = new byte[rawMetadataLen];
- in.readByteArray(rawMetadata);
- } else {
+ byte[] rawMetadata = in.createByteArray();
+ if (rawMetadata == null) {
rawMetadata = new byte[0];
}
int sampleRate = in.readInt();
diff --git a/framework/java/android/bluetooth/BluetoothLeAudioContentMetadata.java b/framework/java/android/bluetooth/BluetoothLeAudioContentMetadata.java
index 89ea28267a..3a032a7bb2 100644
--- a/framework/java/android/bluetooth/BluetoothLeAudioContentMetadata.java
+++ b/framework/java/android/bluetooth/BluetoothLeAudioContentMetadata.java
@@ -132,7 +132,6 @@ public final class BluetoothLeAudioContentMetadata implements Parcelable {
public void writeToParcel(Parcel out, int flags) {
BluetoothUtils.writeStringToParcel(out, mProgramInfo);
BluetoothUtils.writeStringToParcel(out, mLanguage);
- out.writeInt(mRawMetadata.length);
out.writeByteArray(mRawMetadata);
}
@@ -148,9 +147,7 @@ public final class BluetoothLeAudioContentMetadata implements Parcelable {
@NonNull Parcel in) {
final String programInfo = in.readString();
final String language = in.readString();
- final int rawMetadataLength = in.readInt();
- byte[] rawMetadata = new byte[rawMetadataLength];
- in.readByteArray(rawMetadata);
+ byte[] rawMetadata = in.createByteArray();
return new BluetoothLeAudioContentMetadata(programInfo, language, rawMetadata);
}
diff --git a/framework/java/android/bluetooth/BluetoothLeBroadcastReceiveState.java b/framework/java/android/bluetooth/BluetoothLeBroadcastReceiveState.java
index 27d594216a..bfa6741a99 100644
--- a/framework/java/android/bluetooth/BluetoothLeBroadcastReceiveState.java
+++ b/framework/java/android/bluetooth/BluetoothLeBroadcastReceiveState.java
@@ -489,14 +489,7 @@ public final class BluetoothLeBroadcastReceiveState implements Parcelable {
out.writeInt(mBroadcastId);
out.writeInt(mPaSyncState);
out.writeInt(mBigEncryptionState);
-
- if (mBadCode != null) {
- out.writeInt(mBadCode.length);
- out.writeByteArray(mBadCode);
- } else {
- // -1 indicates that there is no "bad broadcast code"
- out.writeInt(-1);
- }
+ out.writeByteArray(mBadCode);
out.writeInt(mNumSubgroups);
out.writeList(mBisSyncState);
out.writeTypedList(mSubgroupMetadata);
@@ -557,15 +550,7 @@ public final class BluetoothLeBroadcastReceiveState implements Parcelable {
final int broadcastId = in.readInt();
final int paSyncState = in.readInt();
final int bigEncryptionState = in.readInt();
- final int badCodeLen = in.readInt();
- byte[] badCode = null;
-
- if (badCodeLen != -1) {
- badCode = new byte[badCodeLen];
- if (badCodeLen > 0) {
- in.readByteArray(badCode);
- }
- }
+ final byte[] badCode = in.createByteArray();
final byte numSubGroups = in.readByte();
final List<Long> bisSyncState =
in.readArrayList(Long.class.getClassLoader(), Long.class);
diff --git a/framework/java/android/bluetooth/BluetoothLeBroadcastSettings.java b/framework/java/android/bluetooth/BluetoothLeBroadcastSettings.java
index 56809f93e9..1c2f7d3226 100644
--- a/framework/java/android/bluetooth/BluetoothLeBroadcastSettings.java
+++ b/framework/java/android/bluetooth/BluetoothLeBroadcastSettings.java
@@ -162,13 +162,7 @@ public final class BluetoothLeBroadcastSettings implements Parcelable {
public void writeToParcel(Parcel out, int flags) {
out.writeBoolean(mIsPublicBroadcast);
BluetoothUtils.writeStringToParcel(out, mBroadcastName);
- if (mBroadcastCode != null) {
- out.writeInt(mBroadcastCode.length);
- out.writeByteArray(mBroadcastCode);
- } else {
- // -1 indicates missing broadcast code
- out.writeInt(-1);
- }
+ out.writeByteArray(mBroadcastCode);
out.writeTypedObject(mPublicBroadcastMetadata, 0);
out.writeTypedList(mSubgroupSettings);
}
@@ -185,14 +179,7 @@ public final class BluetoothLeBroadcastSettings implements Parcelable {
Builder builder = new Builder();
builder.setPublicBroadcast(in.readBoolean());
builder.setBroadcastName(in.readString());
- final int codeLen = in.readInt();
- byte[] broadcastCode = null;
- if (codeLen != -1) {
- broadcastCode = new byte[codeLen];
- if (codeLen >= 0) {
- in.readByteArray(broadcastCode);
- }
- }
+ byte[] broadcastCode = in.createByteArray();
builder.setBroadcastCode(broadcastCode);
builder.setPublicBroadcastMetadata(
in.readTypedObject(BluetoothLeAudioContentMetadata.CREATOR));
diff --git a/system/btif/src/btif_dm.cc b/system/btif/src/btif_dm.cc
index 5848ebba1c..cc52ea4cbd 100644
--- a/system/btif/src/btif_dm.cc
+++ b/system/btif/src/btif_dm.cc
@@ -1313,6 +1313,31 @@ static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event, tBTA_DM_SEARCH*
} break;
case BTA_DM_INQ_RES_EVT: {
+ RawAddress& bdaddr = p_search_data->inq_res.bd_addr;
+
+ // Do not update device properties of already bonded devices.
+ if (com::android::bluetooth::flags::guard_bonded_device_properties() &&
+ btm_sec_is_a_bonded_dev(bdaddr)) {
+ log::debug("Ignore device properties from discovery results for the bonded device: {}",
+ bdaddr);
+
+ bool restrict_report =
+ osi_property_get_bool("bluetooth.restrict_discovered_device.enabled", false);
+ if (restrict_report && p_search_data->inq_res.device_type == BT_DEVICE_TYPE_BLE &&
+ !(p_search_data->inq_res.ble_evt_type & BTM_BLE_CONNECTABLE_MASK)) {
+ log::debug("Ble device {} is not connectable", bdaddr);
+ break;
+ }
+
+ bt_property_t bt_property[] = {
+ {BT_PROPERTY_BDADDR, sizeof(bdaddr), &bdaddr},
+ {BT_PROPERTY_REMOTE_RSSI, sizeof(p_search_data->inq_res.rssi),
+ &(p_search_data->inq_res.rssi)}};
+ GetInterfaceToProfiles()->events->invoke_device_found_cb(ARRAY_SIZE(bt_property),
+ bt_property);
+ break;
+ }
+
/* inquiry result */
bt_bdname_t bdname;
uint8_t remote_name_len = 0;
@@ -1323,7 +1348,6 @@ static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event, tBTA_DM_SEARCH*
p_search_data->inq_res.remt_name_not_required =
check_eir_remote_name(p_search_data, NULL, NULL);
}
- RawAddress& bdaddr = p_search_data->inq_res.bd_addr;
log::verbose("addr:{} device_type=0x{:x}", bdaddr, p_search_data->inq_res.device_type);
bdname.name[0] = 0;
diff --git a/system/main/shim/le_scanning_manager.cc b/system/main/shim/le_scanning_manager.cc
index 8214dea25c..8aaa13ed8b 100644
--- a/system/main/shim/le_scanning_manager.cc
+++ b/system/main/shim/le_scanning_manager.cc
@@ -21,6 +21,7 @@
#include <base/functional/bind.h>
#include <base/threading/thread.h>
#include <bluetooth/log.h>
+#include <com_android_bluetooth_flags.h>
#include <hardware/bluetooth.h>
#include "btif/include/btif_common.h"
@@ -37,6 +38,7 @@
#include "stack/include/advertise_data_parser.h"
#include "stack/include/bt_dev_class.h"
#include "stack/include/btm_log_history.h"
+#include "stack/include/btm_sec_api.h"
#include "stack/include/btm_status.h"
#include "storage/device.h"
#include "storage/le_device.h"
@@ -467,9 +469,13 @@ void BleScannerInterfaceImpl::OnScanResult(uint16_t event_type, uint8_t address_
btm_ble_process_adv_addr(raw_address, &ble_addr_type);
}
- do_in_jni_thread(base::BindOnce(&BleScannerInterfaceImpl::handle_remote_properties,
- base::Unretained(this), raw_address, ble_addr_type,
- advertising_data));
+ // Do not update device properties of already bonded devices.
+ if (!com::android::bluetooth::flags::guard_bonded_device_properties() ||
+ !btm_sec_is_a_bonded_dev(raw_address)) {
+ do_in_jni_thread(base::BindOnce(&BleScannerInterfaceImpl::handle_remote_properties,
+ base::Unretained(this), raw_address, ble_addr_type,
+ advertising_data));
+ }
do_in_jni_thread(base::BindOnce(
&ScanningCallbacks::OnScanResult, base::Unretained(scanning_callbacks_), event_type,
diff --git a/system/stack/avct/avct_lcb_act.cc b/system/stack/avct/avct_lcb_act.cc
index 7770cd9e4a..6b199202de 100644
--- a/system/stack/avct/avct_lcb_act.cc
+++ b/system/stack/avct/avct_lcb_act.cc
@@ -718,10 +718,13 @@ void avct_lcb_msg_ind(tAVCT_LCB* p_lcb, tAVCT_LCB_EVT* p_data) {
p = (uint8_t*)(p_buf + 1) + p_buf->offset;
AVCT_BUILD_HDR(p, label, AVCT_PKT_TYPE_SINGLE, AVCT_REJ);
UINT16_TO_BE_STREAM(p, pid);
+
+ uint16_t len = p_buf->len;
+
if (stack::l2cap::get_interface().L2CA_DataWrite(p_lcb->ch_lcid, p_buf) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} lcid:0x{:04x} len:{}", p_lcb->peer_addr,
- p_lcb->ch_lcid, p_buf->len);
+ p_lcb->ch_lcid, len);
}
}
}
diff --git a/system/stack/avdt/avdt_msg.cc b/system/stack/avdt/avdt_msg.cc
index 09d9c6dd81..eb623b1b2a 100644
--- a/system/stack/avdt/avdt_msg.cc
+++ b/system/stack/avdt/avdt_msg.cc
@@ -29,6 +29,7 @@
#define LOG_TAG "bluetooth-a2dp"
#include <bluetooth/log.h>
+#include <com_android_bluetooth_flags.h>
#include <string.h>
#include <cstdint>
@@ -1544,6 +1545,15 @@ void avdt_msg_ind(AvdtpCcb* p_ccb, BT_HDR* p_buf) {
avdt_msg_send_grej(p_ccb, sig, &msg);
}
}
+
+ /* validate reject/response against cached sig */
+ if (com::android::bluetooth::flags::btsec_avdt_msg_ind_type_confusion()) {
+ if (((msg_type == AVDT_MSG_TYPE_RSP) || (msg_type == AVDT_MSG_TYPE_REJ)) &&
+ (p_ccb->p_curr_cmd == nullptr || p_ccb->p_curr_cmd->event != sig)) {
+ log::warn("Dropping msg with mismatched sig; sig={}", sig);
+ ok = false;
+ }
+ }
}
log::verbose("msg_type={}, sig={}", msg_type, sig);
diff --git a/system/stack/bnep/bnep_main.cc b/system/stack/bnep/bnep_main.cc
index add8bad93d..a9c36379db 100644
--- a/system/stack/bnep/bnep_main.cc
+++ b/system/stack/bnep/bnep_main.cc
@@ -300,10 +300,12 @@ static void bnep_congestion_ind(uint16_t l2cap_cid, bool is_congested) {
break;
}
+ uint16_t len = p_buf->len;
+
if (stack::l2cap::get_interface().L2CA_DataWrite(l2cap_cid, p_buf) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_bcb->rem_bda, l2cap_cid,
- p_buf->len);
+ len);
}
}
}
diff --git a/system/stack/bnep/bnep_utils.cc b/system/stack/bnep/bnep_utils.cc
index 64ea5f2501..7a9a975584 100644
--- a/system/stack/bnep/bnep_utils.cc
+++ b/system/stack/bnep/bnep_utils.cc
@@ -417,10 +417,11 @@ void bnepu_check_send_packet(tBNEP_CONN* p_bcb, BT_HDR* p_buf) {
fixed_queue_enqueue(p_bcb->xmit_q, p_buf);
}
} else {
+ uint16_t len = p_buf->len;
if (stack::l2cap::get_interface().L2CA_DataWrite(p_bcb->l2cap_cid, p_buf) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_bcb->rem_bda,
- p_bcb->l2cap_cid, p_buf->len);
+ p_bcb->l2cap_cid, len);
}
}
}
diff --git a/system/stack/btm/btm_sec.cc b/system/stack/btm/btm_sec.cc
index 9afa217b20..5251baa7eb 100644
--- a/system/stack/btm/btm_sec.cc
+++ b/system/stack/btm/btm_sec.cc
@@ -1397,6 +1397,14 @@ static bool btm_sec_is_upgrade_possible(tBTM_SEC_DEV_REC* p_dev_rec, bool is_ori
* security level database */
is_possible = true;
}
+
+ /*if authentication is requirement & currently on temp bonding
+ * trigger pairing */
+ if (com::android::bluetooth::flags::upgrade_temp_bonding_on_auth_req() &&
+ (p_dev_rec->sec_rec.security_required & BTM_SEC_OUT_AUTHENTICATE) &&
+ p_dev_rec->sec_rec.is_bond_type_temporary()) {
+ is_possible = true;
+ }
}
log::verbose("is_possible: {} sec_flags: 0x{:x}", is_possible, p_dev_rec->sec_rec.sec_flags);
return is_possible;
@@ -3320,6 +3328,10 @@ void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status, uint8_t encr_en
if (status == HCI_ERR_KEY_MISSING) {
log::info("Remote key missing - will report");
bta_dm_remote_key_missing(p_dev_rec->ble.pseudo_addr);
+ if (com::android::bluetooth::flags::sec_disconnect_on_le_key_missing()) {
+ btm_sec_send_hci_disconnect(p_dev_rec, HCI_ERR_HOST_REJECT_SECURITY,
+ p_dev_rec->ble_hci_handle, "encryption_change:key_missing");
+ }
return;
}
@@ -3485,6 +3497,13 @@ void btm_sec_encryption_change_evt(uint16_t handle, tHCI_STATUS status, uint8_t
return;
}
+ if (com::android::bluetooth::flags::disconnect_on_encryption_failure()) {
+ if (status != HCI_SUCCESS && encr_enable == 0) {
+ log::error("Encryption failure {}, disconnecting {}", status, handle);
+ btm_sec_disconnect(handle, HCI_ERR_AUTH_FAILURE,
+ "stack::btu::btu_hcif::encryption_change_evt Encryption Failure");
+ }
+ }
btm_acl_encrypt_change(handle, static_cast<tHCI_STATUS>(status), encr_enable);
btm_sec_encrypt_change(handle, static_cast<tHCI_STATUS>(status), encr_enable, 0);
}
diff --git a/system/stack/hid/hidd_conn.cc b/system/stack/hid/hidd_conn.cc
index b50516d8a8..7276af8acd 100644
--- a/system/stack/hid/hidd_conn.cc
+++ b/system/stack/hid/hidd_conn.cc
@@ -95,10 +95,10 @@ static void hidd_check_config_done() {
// send outstanding data on intr
if (hd_cb.pending_data) {
+ uint16_t len = hd_cb.pending_data->len;
if (stack::l2cap::get_interface().L2CA_DataWrite(p_hcon->intr_cid, hd_cb.pending_data) !=
tL2CAP_DW_RESULT::SUCCESS) {
- log::warn("Unable to write L2CAP data cid:{} len:{}", p_hcon->intr_cid,
- hd_cb.pending_data->len);
+ log::warn("Unable to write L2CAP data cid:{} len:{}", p_hcon->intr_cid, len);
}
hd_cb.pending_data = NULL;
}
diff --git a/system/stack/rfcomm/rfc_ts_frames.cc b/system/stack/rfcomm/rfc_ts_frames.cc
index fe92bb7ef0..957ace7b7f 100644
--- a/system/stack/rfcomm/rfc_ts_frames.cc
+++ b/system/stack/rfcomm/rfc_ts_frames.cc
@@ -197,10 +197,11 @@ void rfc_send_buf_uih(tRFC_MCB* p_mcb, uint8_t dlci, BT_HDR* p_buf) {
if (dlci == RFCOMM_MX_DLCI) {
rfc_check_send_cmd(p_mcb, p_buf);
} else {
+ uint16_t len = p_buf->len;
if (stack::l2cap::get_interface().L2CA_DataWrite(p_mcb->lcid, p_buf) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_mcb->bd_addr, p_mcb->lcid,
- p_buf->len);
+ len);
}
}
}
diff --git a/system/stack/rfcomm/rfc_utils.cc b/system/stack/rfcomm/rfc_utils.cc
index 87beaaf566..55845a9f76 100644
--- a/system/stack/rfcomm/rfc_utils.cc
+++ b/system/stack/rfcomm/rfc_utils.cc
@@ -428,9 +428,10 @@ void rfc_check_send_cmd(tRFC_MCB* p_mcb, BT_HDR* p_buf) {
if (p == NULL) {
break;
}
+ uint16_t len = p->len;
if (stack::l2cap::get_interface().L2CA_DataWrite(p_mcb->lcid, p) != tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_mcb->bd_addr, p_mcb->lcid,
- p->len);
+ len);
}
}
}
diff --git a/system/stack/sdp/sdp_discovery.cc b/system/stack/sdp/sdp_discovery.cc
index d3284892c8..6aba1993af 100644
--- a/system/stack/sdp/sdp_discovery.cc
+++ b/system/stack/sdp/sdp_discovery.cc
@@ -180,7 +180,7 @@ static void sdp_snd_service_search_req(tCONN_CB* p_ccb, uint8_t cont_len, uint8_
if (stack::l2cap::get_interface().L2CA_DataWrite(p_ccb->connection_id, p_cmd) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_ccb->device_address,
- p_ccb->connection_id, p_cmd->len);
+ p_ccb->connection_id, p - p_start);
}
/* Start inactivity timer */
@@ -708,7 +708,7 @@ static void process_service_search_attr_rsp(tCONN_CB* p_ccb, uint8_t* p_reply,
if (stack::l2cap::get_interface().L2CA_DataWrite(p_ccb->connection_id, p_msg) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_ccb->device_address,
- p_ccb->connection_id, p_msg->len);
+ p_ccb->connection_id, p - p_start);
}
/* Start inactivity timer */
@@ -877,7 +877,7 @@ static void process_service_attr_rsp(tCONN_CB* p_ccb, uint8_t* p_reply, uint8_t*
if (stack::l2cap::get_interface().L2CA_DataWrite(p_ccb->connection_id, p_msg) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_ccb->device_address,
- p_ccb->connection_id, p_msg->len);
+ p_ccb->connection_id, p - p_start);
}
/* Start inactivity timer */
diff --git a/system/stack/sdp/sdp_server.cc b/system/stack/sdp/sdp_server.cc
index 864280cba4..0f379708e9 100644
--- a/system/stack/sdp/sdp_server.cc
+++ b/system/stack/sdp/sdp_server.cc
@@ -300,7 +300,7 @@ static void process_service_search(tCONN_CB* p_ccb, uint16_t trans_num, uint16_t
if (stack::l2cap::get_interface().L2CA_DataWrite(p_ccb->connection_id, p_buf) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_ccb->device_address,
- p_ccb->connection_id, p_buf->len);
+ p_ccb->connection_id, p_rsp - p_rsp_start);
}
}
@@ -564,7 +564,7 @@ static void process_service_attr_req(tCONN_CB* p_ccb, uint16_t trans_num, uint16
if (stack::l2cap::get_interface().L2CA_DataWrite(p_ccb->connection_id, p_buf) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_ccb->device_address,
- p_ccb->connection_id, p_buf->len);
+ p_ccb->connection_id, p_rsp - p_rsp_start);
}
}
@@ -921,7 +921,7 @@ static void process_service_search_attr_req(tCONN_CB* p_ccb, uint16_t trans_num,
if (stack::l2cap::get_interface().L2CA_DataWrite(p_ccb->connection_id, p_buf) !=
tL2CAP_DW_RESULT::SUCCESS) {
log::warn("Unable to write L2CAP data peer:{} cid:{} len:{}", p_ccb->device_address,
- p_ccb->connection_id, p_buf->len);
+ p_ccb->connection_id, p_rsp - p_rsp_start);
}
}
diff --git a/system/stack/smp/smp_act.cc b/system/stack/smp/smp_act.cc
index c625217c7c..a9a8aafbf7 100644
--- a/system/stack/smp/smp_act.cc
+++ b/system/stack/smp/smp_act.cc
@@ -1954,6 +1954,18 @@ void smp_process_secure_connection_oob_data(tSMP_CB* p_cb, tSMP_INT_DATA* /* p_d
p_cb->local_random = {0};
}
+ if (com::android::bluetooth::flags::btsec_le_oob_pairing()) {
+ if (p_cb->peer_oob_flag == SMP_OOB_PRESENT && !p_sc_oob_data->loc_oob_data.present) {
+ log::warn(
+ "local OOB data is not present but peer claims to have received it; dropping "
+ "connection");
+ tSMP_INT_DATA smp_int_data{};
+ smp_int_data.status = SMP_OOB_FAIL;
+ smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &smp_int_data);
+ return;
+ }
+ }
+
if (!p_sc_oob_data->peer_oob_data.present) {
log::verbose("peer OOB data is absent");
p_cb->peer_random = {0};