Loading android/app/src/com/android/bluetooth/pan/PanService.java +20 −31 Original line number Diff line number Diff line Loading @@ -70,10 +70,12 @@ public class PanService extends ProfileService { private static final int BLUETOOTH_MAX_PAN_CONNECTIONS = 5; private static final int BLUETOOTH_PREFIX_LENGTH = 24; private HashMap<BluetoothDevice, BluetoothPanDevice> mPanDevices; @VisibleForTesting HashMap<BluetoothDevice, BluetoothPanDevice> mPanDevices; private int mMaxPanDevices; private String mPanIfName; private boolean mIsTethering = false; @VisibleForTesting boolean mIsTethering = false; private boolean mNativeAvailable; private HashMap<String, IBluetoothPanCallback> mBluetoothTetheringCallbacks; Loading Loading @@ -602,9 +604,8 @@ public class PanService extends ProfileService { public int remote_role; } ; private void onConnectStateChanged(byte[] address, int state, int error, int localRole, @VisibleForTesting void onConnectStateChanged(byte[] address, int state, int error, int localRole, int remoteRole) { if (DBG) { Log.d(TAG, "onConnectStateChanged: " + state + ", local role:" + localRole Loading @@ -615,7 +616,8 @@ public class PanService extends ProfileService { mHandler.sendMessage(msg); } private void onControlStateChanged(int localRole, int state, int error, String ifname) { @VisibleForTesting void onControlStateChanged(int localRole, int state, int error, String ifname) { if (DBG) { Log.d(TAG, "onControlStateChanged: " + state + ", error: " + error + ", ifname: " + ifname); Loading @@ -625,7 +627,8 @@ public class PanService extends ProfileService { } } private static int convertHalState(int halState) { @VisibleForTesting static int convertHalState(int halState) { switch (halState) { case CONN_STATE_CONNECTED: return BluetoothProfile.STATE_CONNECTED; Loading Loading @@ -748,25 +751,6 @@ public class PanService extends ProfileService { sendBroadcast(intent, BLUETOOTH_CONNECT); } private List<BluetoothDevice> getConnectedPanDevices() { List<BluetoothDevice> devices = new ArrayList<BluetoothDevice>(); for (BluetoothDevice device : mPanDevices.keySet()) { if (getPanDeviceConnectionState(device) == BluetoothProfile.STATE_CONNECTED) { devices.add(device); } } return devices; } private int getPanDeviceConnectionState(BluetoothDevice device) { BluetoothPanDevice panDevice = mPanDevices.get(device); if (panDevice == null) { return BluetoothProfile.STATE_DISCONNECTED; } return panDevice.mState; } @Override public void dump(StringBuilder sb) { super.dump(sb); Loading @@ -779,7 +763,8 @@ public class PanService extends ProfileService { } } private class BluetoothPanDevice { @VisibleForTesting static class BluetoothPanDevice { private int mState; private String mIface; private int mLocalRole; // Which local role is this PAN device bound to Loading @@ -795,10 +780,14 @@ public class PanService extends ProfileService { // Constants matching Hal header file bt_hh.h // bthh_connection_state_t private static final int CONN_STATE_CONNECTED = 0; private static final int CONN_STATE_CONNECTING = 1; private static final int CONN_STATE_DISCONNECTED = 2; private static final int CONN_STATE_DISCONNECTING = 3; @VisibleForTesting static final int CONN_STATE_CONNECTED = 0; @VisibleForTesting static final int CONN_STATE_CONNECTING = 1; @VisibleForTesting static final int CONN_STATE_DISCONNECTED = 2; @VisibleForTesting static final int CONN_STATE_DISCONNECTING = 3; private static native void classInitNative(); Loading android/app/tests/unit/src/com/android/bluetooth/pan/PanServiceTest.java +130 −14 Original line number Diff line number Diff line Loading @@ -15,27 +15,32 @@ */ package com.android.bluetooth.pan; import static android.bluetooth.BluetoothPan.PAN_ROLE_NONE; import static android.net.TetheringManager.TETHERING_BLUETOOTH; import static android.net.TetheringManager.TETHER_ERROR_SERVICE_UNAVAIL; import static com.google.common.truth.Truth.assertThat; import static org.mockito.Mockito.anyString; import static org.mockito.Mockito.doReturn; import static org.mockito.Mockito.when; import android.bluetooth.BluetoothAdapter; import android.bluetooth.BluetoothDevice; import android.content.Context; import android.bluetooth.BluetoothProfile; import android.net.TetheringInterface; import android.os.UserManager; import androidx.test.InstrumentationRegistry; import androidx.test.filters.MediumTest; import androidx.test.rule.ServiceTestRule; import androidx.test.runner.AndroidJUnit4; import com.android.bluetooth.R; import com.android.bluetooth.TestUtils; import com.android.bluetooth.btservice.AdapterService; import com.android.bluetooth.btservice.storage.DatabaseManager; import com.android.bluetooth.pan.PanService.BluetoothPanDevice; import org.junit.After; import org.junit.Assert; import org.junit.Assume; import org.junit.Before; import org.junit.Rule; Loading @@ -47,9 +52,12 @@ import org.mockito.MockitoAnnotations; @MediumTest @RunWith(AndroidJUnit4.class) public class PanServiceTest { private static final String REMOTE_DEVICE_ADDRESS = "00:00:00:00:00:00"; private static final byte[] REMOTE_DEVICE_ADDRESS_AS_ARRAY = new byte[] {0, 0, 0, 0, 0, 0}; private PanService mService = null; private BluetoothAdapter mAdapter = null; private Context mTargetContext; private BluetoothDevice mRemoteDevice; @Rule public final ServiceTestRule mServiceRule = new ServiceTestRule(); Loading @@ -59,7 +67,6 @@ public class PanServiceTest { @Before public void setUp() throws Exception { mTargetContext = InstrumentationRegistry.getTargetContext(); Assume.assumeTrue("Ignore test when PanService is not enabled", PanService.isEnabled()); MockitoAnnotations.initMocks(this); Loading @@ -68,11 +75,12 @@ public class PanServiceTest { doReturn(true, false).when(mAdapterService).isStartedProfile(anyString()); TestUtils.startService(mServiceRule, PanService.class); mService = PanService.getPanService(); Assert.assertNotNull(mService); assertThat(mService).isNotNull(); // Try getting the Bluetooth adapter mAdapter = BluetoothAdapter.getDefaultAdapter(); Assert.assertNotNull(mAdapter); assertThat(mAdapter).isNotNull(); mService.mUserManager = mMockUserManager; mRemoteDevice = mAdapter.getRemoteDevice(REMOTE_DEVICE_ADDRESS); } @After Loading @@ -82,19 +90,127 @@ public class PanServiceTest { } TestUtils.stopService(mServiceRule, PanService.class); mService = PanService.getPanService(); Assert.assertNull(mService); assertThat(mService).isNull(); TestUtils.clearAdapterService(mAdapterService); } @Test public void testInitialize() { Assert.assertNotNull(PanService.getPanService()); public void initialize() { assertThat(PanService.getPanService()).isNotNull(); } @Test public void testGuestUserConnect() { BluetoothDevice device = TestUtils.getTestDevice(mAdapter, 0); public void connect_whenGuestUser_returnsFalse() { when(mMockUserManager.isGuestUser()).thenReturn(true); Assert.assertFalse(mService.connect(device)); assertThat(mService.connect(mRemoteDevice)).isFalse(); } @Test public void connect_inConnectedState_returnsFalse() { when(mMockUserManager.isGuestUser()).thenReturn(false); mService.mPanDevices.put(mRemoteDevice, new BluetoothPanDevice( BluetoothProfile.STATE_CONNECTED, "iface", PAN_ROLE_NONE, PAN_ROLE_NONE)); assertThat(mService.connect(mRemoteDevice)).isFalse(); } @Test public void connect() { when(mMockUserManager.isGuestUser()).thenReturn(false); mService.mPanDevices.put(mRemoteDevice, new BluetoothPanDevice( BluetoothProfile.STATE_DISCONNECTED, "iface", PAN_ROLE_NONE, PAN_ROLE_NONE)); assertThat(mService.connect(mRemoteDevice)).isTrue(); } @Test public void disconnect_returnsTrue() { assertThat(mService.disconnect(mRemoteDevice)).isTrue(); } @Test public void convertHalState() { assertThat(PanService.convertHalState(PanService.CONN_STATE_CONNECTED)) .isEqualTo(BluetoothProfile.STATE_CONNECTED); assertThat(PanService.convertHalState(PanService.CONN_STATE_CONNECTING)) .isEqualTo(BluetoothProfile.STATE_CONNECTING); assertThat(PanService.convertHalState(PanService.CONN_STATE_DISCONNECTED)) .isEqualTo(BluetoothProfile.STATE_DISCONNECTED); assertThat(PanService.convertHalState(PanService.CONN_STATE_DISCONNECTING)) .isEqualTo(BluetoothProfile.STATE_DISCONNECTING); assertThat(PanService.convertHalState(-24664)) // illegal value .isEqualTo(BluetoothProfile.STATE_DISCONNECTED); } @Test public void dump() { mService.mPanDevices.put(mRemoteDevice, new BluetoothPanDevice( BluetoothProfile.STATE_DISCONNECTED, "iface", PAN_ROLE_NONE, PAN_ROLE_NONE)); mService.dump(new StringBuilder()); } @Test public void onConnectStateChanged_doesNotCrash() { mService.onConnectStateChanged(REMOTE_DEVICE_ADDRESS_AS_ARRAY, 1, 2, 3, 4); } @Test public void onControlStateChanged_doesNotCrash() { mService.onControlStateChanged(1, 2, 3, "ifname"); } @Test public void setConnectionPolicy_whenDatabaseManagerRefuses_returnsFalse() { int connectionPolicy = BluetoothProfile.CONNECTION_POLICY_ALLOWED; when(mDatabaseManager.setProfileConnectionPolicy( mRemoteDevice, BluetoothProfile.PAN, connectionPolicy)).thenReturn(false); assertThat(mService.setConnectionPolicy(mRemoteDevice, connectionPolicy)).isFalse(); } @Test public void setConnectionPolicy_returnsTrue() { when(mDatabaseManager.setProfileConnectionPolicy( mRemoteDevice, BluetoothProfile.PAN, BluetoothProfile.CONNECTION_POLICY_ALLOWED)) .thenReturn(true); assertThat(mService.setConnectionPolicy( mRemoteDevice, BluetoothProfile.CONNECTION_POLICY_ALLOWED)).isTrue(); when(mDatabaseManager.setProfileConnectionPolicy( mRemoteDevice, BluetoothProfile.PAN, BluetoothProfile.CONNECTION_POLICY_FORBIDDEN)) .thenReturn(true); assertThat(mService.setConnectionPolicy( mRemoteDevice, BluetoothProfile.CONNECTION_POLICY_FORBIDDEN)).isTrue(); } @Test public void connectState_constructor() { int state = 1; int error = 2; int localRole = 3; int remoteRole = 4; PanService.ConnectState connectState = new PanService.ConnectState( REMOTE_DEVICE_ADDRESS_AS_ARRAY, state, error, localRole, remoteRole); assertThat(connectState.addr).isEqualTo(REMOTE_DEVICE_ADDRESS_AS_ARRAY); assertThat(connectState.state).isEqualTo(state); assertThat(connectState.error).isEqualTo(error); assertThat(connectState.local_role).isEqualTo(localRole); assertThat(connectState.remote_role).isEqualTo(remoteRole); } @Test public void tetheringCallback_onError_clearsPanDevices() { mService.mIsTethering = true; mService.mPanDevices.put(mRemoteDevice, new BluetoothPanDevice( BluetoothProfile.STATE_DISCONNECTED, "iface", PAN_ROLE_NONE, PAN_ROLE_NONE)); TetheringInterface iface = new TetheringInterface(TETHERING_BLUETOOTH, "iface"); mService.mTetheringCallback.onError(iface, TETHER_ERROR_SERVICE_UNAVAIL); assertThat(mService.mPanDevices).isEmpty(); assertThat(mService.mIsTethering).isFalse(); } } Loading
android/app/src/com/android/bluetooth/pan/PanService.java +20 −31 Original line number Diff line number Diff line Loading @@ -70,10 +70,12 @@ public class PanService extends ProfileService { private static final int BLUETOOTH_MAX_PAN_CONNECTIONS = 5; private static final int BLUETOOTH_PREFIX_LENGTH = 24; private HashMap<BluetoothDevice, BluetoothPanDevice> mPanDevices; @VisibleForTesting HashMap<BluetoothDevice, BluetoothPanDevice> mPanDevices; private int mMaxPanDevices; private String mPanIfName; private boolean mIsTethering = false; @VisibleForTesting boolean mIsTethering = false; private boolean mNativeAvailable; private HashMap<String, IBluetoothPanCallback> mBluetoothTetheringCallbacks; Loading Loading @@ -602,9 +604,8 @@ public class PanService extends ProfileService { public int remote_role; } ; private void onConnectStateChanged(byte[] address, int state, int error, int localRole, @VisibleForTesting void onConnectStateChanged(byte[] address, int state, int error, int localRole, int remoteRole) { if (DBG) { Log.d(TAG, "onConnectStateChanged: " + state + ", local role:" + localRole Loading @@ -615,7 +616,8 @@ public class PanService extends ProfileService { mHandler.sendMessage(msg); } private void onControlStateChanged(int localRole, int state, int error, String ifname) { @VisibleForTesting void onControlStateChanged(int localRole, int state, int error, String ifname) { if (DBG) { Log.d(TAG, "onControlStateChanged: " + state + ", error: " + error + ", ifname: " + ifname); Loading @@ -625,7 +627,8 @@ public class PanService extends ProfileService { } } private static int convertHalState(int halState) { @VisibleForTesting static int convertHalState(int halState) { switch (halState) { case CONN_STATE_CONNECTED: return BluetoothProfile.STATE_CONNECTED; Loading Loading @@ -748,25 +751,6 @@ public class PanService extends ProfileService { sendBroadcast(intent, BLUETOOTH_CONNECT); } private List<BluetoothDevice> getConnectedPanDevices() { List<BluetoothDevice> devices = new ArrayList<BluetoothDevice>(); for (BluetoothDevice device : mPanDevices.keySet()) { if (getPanDeviceConnectionState(device) == BluetoothProfile.STATE_CONNECTED) { devices.add(device); } } return devices; } private int getPanDeviceConnectionState(BluetoothDevice device) { BluetoothPanDevice panDevice = mPanDevices.get(device); if (panDevice == null) { return BluetoothProfile.STATE_DISCONNECTED; } return panDevice.mState; } @Override public void dump(StringBuilder sb) { super.dump(sb); Loading @@ -779,7 +763,8 @@ public class PanService extends ProfileService { } } private class BluetoothPanDevice { @VisibleForTesting static class BluetoothPanDevice { private int mState; private String mIface; private int mLocalRole; // Which local role is this PAN device bound to Loading @@ -795,10 +780,14 @@ public class PanService extends ProfileService { // Constants matching Hal header file bt_hh.h // bthh_connection_state_t private static final int CONN_STATE_CONNECTED = 0; private static final int CONN_STATE_CONNECTING = 1; private static final int CONN_STATE_DISCONNECTED = 2; private static final int CONN_STATE_DISCONNECTING = 3; @VisibleForTesting static final int CONN_STATE_CONNECTED = 0; @VisibleForTesting static final int CONN_STATE_CONNECTING = 1; @VisibleForTesting static final int CONN_STATE_DISCONNECTED = 2; @VisibleForTesting static final int CONN_STATE_DISCONNECTING = 3; private static native void classInitNative(); Loading
android/app/tests/unit/src/com/android/bluetooth/pan/PanServiceTest.java +130 −14 Original line number Diff line number Diff line Loading @@ -15,27 +15,32 @@ */ package com.android.bluetooth.pan; import static android.bluetooth.BluetoothPan.PAN_ROLE_NONE; import static android.net.TetheringManager.TETHERING_BLUETOOTH; import static android.net.TetheringManager.TETHER_ERROR_SERVICE_UNAVAIL; import static com.google.common.truth.Truth.assertThat; import static org.mockito.Mockito.anyString; import static org.mockito.Mockito.doReturn; import static org.mockito.Mockito.when; import android.bluetooth.BluetoothAdapter; import android.bluetooth.BluetoothDevice; import android.content.Context; import android.bluetooth.BluetoothProfile; import android.net.TetheringInterface; import android.os.UserManager; import androidx.test.InstrumentationRegistry; import androidx.test.filters.MediumTest; import androidx.test.rule.ServiceTestRule; import androidx.test.runner.AndroidJUnit4; import com.android.bluetooth.R; import com.android.bluetooth.TestUtils; import com.android.bluetooth.btservice.AdapterService; import com.android.bluetooth.btservice.storage.DatabaseManager; import com.android.bluetooth.pan.PanService.BluetoothPanDevice; import org.junit.After; import org.junit.Assert; import org.junit.Assume; import org.junit.Before; import org.junit.Rule; Loading @@ -47,9 +52,12 @@ import org.mockito.MockitoAnnotations; @MediumTest @RunWith(AndroidJUnit4.class) public class PanServiceTest { private static final String REMOTE_DEVICE_ADDRESS = "00:00:00:00:00:00"; private static final byte[] REMOTE_DEVICE_ADDRESS_AS_ARRAY = new byte[] {0, 0, 0, 0, 0, 0}; private PanService mService = null; private BluetoothAdapter mAdapter = null; private Context mTargetContext; private BluetoothDevice mRemoteDevice; @Rule public final ServiceTestRule mServiceRule = new ServiceTestRule(); Loading @@ -59,7 +67,6 @@ public class PanServiceTest { @Before public void setUp() throws Exception { mTargetContext = InstrumentationRegistry.getTargetContext(); Assume.assumeTrue("Ignore test when PanService is not enabled", PanService.isEnabled()); MockitoAnnotations.initMocks(this); Loading @@ -68,11 +75,12 @@ public class PanServiceTest { doReturn(true, false).when(mAdapterService).isStartedProfile(anyString()); TestUtils.startService(mServiceRule, PanService.class); mService = PanService.getPanService(); Assert.assertNotNull(mService); assertThat(mService).isNotNull(); // Try getting the Bluetooth adapter mAdapter = BluetoothAdapter.getDefaultAdapter(); Assert.assertNotNull(mAdapter); assertThat(mAdapter).isNotNull(); mService.mUserManager = mMockUserManager; mRemoteDevice = mAdapter.getRemoteDevice(REMOTE_DEVICE_ADDRESS); } @After Loading @@ -82,19 +90,127 @@ public class PanServiceTest { } TestUtils.stopService(mServiceRule, PanService.class); mService = PanService.getPanService(); Assert.assertNull(mService); assertThat(mService).isNull(); TestUtils.clearAdapterService(mAdapterService); } @Test public void testInitialize() { Assert.assertNotNull(PanService.getPanService()); public void initialize() { assertThat(PanService.getPanService()).isNotNull(); } @Test public void testGuestUserConnect() { BluetoothDevice device = TestUtils.getTestDevice(mAdapter, 0); public void connect_whenGuestUser_returnsFalse() { when(mMockUserManager.isGuestUser()).thenReturn(true); Assert.assertFalse(mService.connect(device)); assertThat(mService.connect(mRemoteDevice)).isFalse(); } @Test public void connect_inConnectedState_returnsFalse() { when(mMockUserManager.isGuestUser()).thenReturn(false); mService.mPanDevices.put(mRemoteDevice, new BluetoothPanDevice( BluetoothProfile.STATE_CONNECTED, "iface", PAN_ROLE_NONE, PAN_ROLE_NONE)); assertThat(mService.connect(mRemoteDevice)).isFalse(); } @Test public void connect() { when(mMockUserManager.isGuestUser()).thenReturn(false); mService.mPanDevices.put(mRemoteDevice, new BluetoothPanDevice( BluetoothProfile.STATE_DISCONNECTED, "iface", PAN_ROLE_NONE, PAN_ROLE_NONE)); assertThat(mService.connect(mRemoteDevice)).isTrue(); } @Test public void disconnect_returnsTrue() { assertThat(mService.disconnect(mRemoteDevice)).isTrue(); } @Test public void convertHalState() { assertThat(PanService.convertHalState(PanService.CONN_STATE_CONNECTED)) .isEqualTo(BluetoothProfile.STATE_CONNECTED); assertThat(PanService.convertHalState(PanService.CONN_STATE_CONNECTING)) .isEqualTo(BluetoothProfile.STATE_CONNECTING); assertThat(PanService.convertHalState(PanService.CONN_STATE_DISCONNECTED)) .isEqualTo(BluetoothProfile.STATE_DISCONNECTED); assertThat(PanService.convertHalState(PanService.CONN_STATE_DISCONNECTING)) .isEqualTo(BluetoothProfile.STATE_DISCONNECTING); assertThat(PanService.convertHalState(-24664)) // illegal value .isEqualTo(BluetoothProfile.STATE_DISCONNECTED); } @Test public void dump() { mService.mPanDevices.put(mRemoteDevice, new BluetoothPanDevice( BluetoothProfile.STATE_DISCONNECTED, "iface", PAN_ROLE_NONE, PAN_ROLE_NONE)); mService.dump(new StringBuilder()); } @Test public void onConnectStateChanged_doesNotCrash() { mService.onConnectStateChanged(REMOTE_DEVICE_ADDRESS_AS_ARRAY, 1, 2, 3, 4); } @Test public void onControlStateChanged_doesNotCrash() { mService.onControlStateChanged(1, 2, 3, "ifname"); } @Test public void setConnectionPolicy_whenDatabaseManagerRefuses_returnsFalse() { int connectionPolicy = BluetoothProfile.CONNECTION_POLICY_ALLOWED; when(mDatabaseManager.setProfileConnectionPolicy( mRemoteDevice, BluetoothProfile.PAN, connectionPolicy)).thenReturn(false); assertThat(mService.setConnectionPolicy(mRemoteDevice, connectionPolicy)).isFalse(); } @Test public void setConnectionPolicy_returnsTrue() { when(mDatabaseManager.setProfileConnectionPolicy( mRemoteDevice, BluetoothProfile.PAN, BluetoothProfile.CONNECTION_POLICY_ALLOWED)) .thenReturn(true); assertThat(mService.setConnectionPolicy( mRemoteDevice, BluetoothProfile.CONNECTION_POLICY_ALLOWED)).isTrue(); when(mDatabaseManager.setProfileConnectionPolicy( mRemoteDevice, BluetoothProfile.PAN, BluetoothProfile.CONNECTION_POLICY_FORBIDDEN)) .thenReturn(true); assertThat(mService.setConnectionPolicy( mRemoteDevice, BluetoothProfile.CONNECTION_POLICY_FORBIDDEN)).isTrue(); } @Test public void connectState_constructor() { int state = 1; int error = 2; int localRole = 3; int remoteRole = 4; PanService.ConnectState connectState = new PanService.ConnectState( REMOTE_DEVICE_ADDRESS_AS_ARRAY, state, error, localRole, remoteRole); assertThat(connectState.addr).isEqualTo(REMOTE_DEVICE_ADDRESS_AS_ARRAY); assertThat(connectState.state).isEqualTo(state); assertThat(connectState.error).isEqualTo(error); assertThat(connectState.local_role).isEqualTo(localRole); assertThat(connectState.remote_role).isEqualTo(remoteRole); } @Test public void tetheringCallback_onError_clearsPanDevices() { mService.mIsTethering = true; mService.mPanDevices.put(mRemoteDevice, new BluetoothPanDevice( BluetoothProfile.STATE_DISCONNECTED, "iface", PAN_ROLE_NONE, PAN_ROLE_NONE)); TetheringInterface iface = new TetheringInterface(TETHERING_BLUETOOTH, "iface"); mService.mTetheringCallback.onError(iface, TETHER_ERROR_SERVICE_UNAVAIL); assertThat(mService.mPanDevices).isEmpty(); assertThat(mService.mIsTethering).isFalse(); } }