From 382872e3fa45fb1433976b7bda4b26bbc2072f71 Mon Sep 17 00:00:00 2001 From: Joe Onorato Date: Thu, 26 Aug 2010 14:46:01 -0400 Subject: [PATCH 01/10] Continue trying to make the turn off quickly after call feature work. The previous implementation worked if the set timeout is short enough, which mine was. This one carries the remaining amount of timeout override forward through all of the countdown steps. Bug: 2844990 Change-Id: I040df22f9f9ddf98c355ac6845b7624e95f84f33 --- .../com/android/server/PowerManagerService.java | 17 ++++++++++++----- 1 file changed, 12 insertions(+), 5 deletions(-) diff --git a/services/java/com/android/server/PowerManagerService.java b/services/java/com/android/server/PowerManagerService.java index 7bbc32ffec286..55f9d60d78cca 100644 --- a/services/java/com/android/server/PowerManagerService.java +++ b/services/java/com/android/server/PowerManagerService.java @@ -1029,11 +1029,10 @@ class PowerManagerService extends IPowerManager.Stub // If they gave a timeoutOverride it is the number of seconds // to screen-off. Figure out where in the countdown cycle we // should jump to. - private void setTimeoutLocked(long now, long timeoutOverride, int nextState) { + private void setTimeoutLocked(long now, final long originalTimeoutOverride, int nextState) { + long timeoutOverride = originalTimeoutOverride; if (mBootCompleted) { synchronized (mLocks) { - mHandler.removeCallbacks(mTimeoutTask); - mTimeoutTask.nextState = nextState; long when = 0; if (timeoutOverride <= 0) { switch (nextState) @@ -1084,6 +1083,12 @@ class PowerManagerService extends IPowerManager.Stub + " timeoutOverride=" + timeoutOverride + " nextState=" + nextState + " when=" + when); } + + mHandler.removeCallbacks(mTimeoutTask); + mTimeoutTask.nextState = nextState; + mTimeoutTask.remainingTimeoutOverride = timeoutOverride > 0 + ? (originalTimeoutOverride - timeoutOverride) + : -1; mHandler.postAtTime(mTimeoutTask, when); mNextTimeout = when; // for debugging } @@ -1099,6 +1104,7 @@ class PowerManagerService extends IPowerManager.Stub private class TimeoutTask implements Runnable { int nextState; // access should be synchronized on mLocks + long remainingTimeoutOverride; public void run() { synchronized (mLocks) { @@ -1119,11 +1125,11 @@ class PowerManagerService extends IPowerManager.Stub { case SCREEN_BRIGHT: if (mDimDelay >= 0) { - setTimeoutLocked(now, SCREEN_DIM); + setTimeoutLocked(now, remainingTimeoutOverride, SCREEN_DIM); break; } case SCREEN_DIM: - setTimeoutLocked(now, SCREEN_OFF); + setTimeoutLocked(now, remainingTimeoutOverride, SCREEN_OFF); break; } } @@ -2054,6 +2060,7 @@ class PowerManagerService extends IPowerManager.Stub + " mUserState=0x" + Integer.toHexString(mUserState) + " mWakeLockState=0x" + Integer.toHexString(mWakeLockState) + " mProximitySensorActive=" + mProximitySensorActive + + " timeoutOverride=" + timeoutOverride + " force=" + force); } // ignore user activity if we are in the process of turning off the screen From 102f6806a8b54822b4c2b6bb55741b0437bc6c98 Mon Sep 17 00:00:00 2001 From: Doug Zongker Date: Thu, 19 Aug 2010 13:38:26 -0700 Subject: [PATCH 02/10] make android_id random seed depend on time as well as ro.serialno Change-Id: I0a48aacd8da30896d91fa05b7791335e6ed751e5 --- .../providers/settings/SettingsProvider.java | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-) diff --git a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java index 4372cd89e0868..54346941b0fa4 100644 --- a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java +++ b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java @@ -222,16 +222,11 @@ public class SettingsProvider extends ContentProvider { final String value = c.moveToNext() ? c.getString(0) : null; if (value == null) { final SecureRandom random = SecureRandom.getInstance("SHA1PRNG"); - String serial = SystemProperties.get("ro.serialno"); - if (serial != null) { - try { - random.setSeed(serial.getBytes("UTF-8")); - } catch (UnsupportedEncodingException ignore) { - // stick with default seed - } - } + String serial = SystemProperties.get("ro.serialno", ""); + random.setSeed( + (serial + System.nanoTime() + new SecureRandom().nextLong()).getBytes()); final String newAndroidIdValue = Long.toHexString(random.nextLong()); - Log.d(TAG, "Generated and saved new ANDROID_ID"); + Log.d(TAG, "Generated and saved new ANDROID_ID [" + newAndroidIdValue + "]"); final ContentValues values = new ContentValues(); values.put(Settings.NameValueTable.NAME, Settings.Secure.ANDROID_ID); values.put(Settings.NameValueTable.VALUE, newAndroidIdValue); From 03b42286888e172641e6846627568a6bc738f824 Mon Sep 17 00:00:00 2001 From: Christopher Tate Date: Tue, 24 Aug 2010 15:37:42 -0700 Subject: [PATCH 03/10] Make the default backup configuration "disabled; local transport selected" By default out of the box, an Android build will have the backup mechanism in its "disabled" state and pointed to the LocalTransport test transport. We do not want retail devices built without the Google backend to have backup enabled out of the box; it would cause them to gradually grind away the cache partition for no good reason. On those devices with this change, developers would need to enable backup manually (possibly using the normal Settings UI; more probably using the 'bmgr' shell tool), but would no longer also have to manually configure the active transport name. Device vendors producing Google-enabled products will simply use resource overlays to configure the default state and transport name for their builds. When building a product that points to the Google backup transport by default, the "def_backup_enabled" boolean resource should still be set to 'false' -- the Google backup disclosure activity supplied by GSF will take care of enabling the backup services if the user opts in to it. (Basically, vendors will never have to overlay the def_backup_enabled resource -- the default value of 'false' is correct for any retail device regardless of whether it can use the Google backup transport.) In the SDK build, the default transport will remain the local one, but the default enable state overridden and set to "true". This is the ideal situation for developers: all aspects of the backup mechanism immediately operative with no manual configuration needed. Change-Id: I866f8f627b023b338bc7757e61604e6d8a901a34 --- packages/SettingsProvider/res/values/defaults.xml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/packages/SettingsProvider/res/values/defaults.xml b/packages/SettingsProvider/res/values/defaults.xml index 185d72a966e3a..8349fe6fa7978 100644 --- a/packages/SettingsProvider/res/values/defaults.xml +++ b/packages/SettingsProvider/res/values/defaults.xml @@ -47,7 +47,8 @@ true false - + android/com.android.internal.backup.LocalTransport + true From c6bab7d4ba474a0f414b76be4e655c9ed9103f2d Mon Sep 17 00:00:00 2001 From: Wink Saville Date: Fri, 20 Aug 2010 16:24:02 -0700 Subject: [PATCH 04/10] Change CDMAPhone.getDeviceId to return MEID or ESN. This allows devices with only ESN's to work. bug: 2938223 Change-Id: I33939151c59f598b939e73d98f1178669d6ceb75 --- telephony/java/android/telephony/TelephonyManager.java | 2 +- .../com/android/internal/telephony/cdma/CDMAPhone.java | 9 +++++++-- 2 files changed, 8 insertions(+), 3 deletions(-) diff --git a/telephony/java/android/telephony/TelephonyManager.java b/telephony/java/android/telephony/TelephonyManager.java index 4ee95609c3e1b..278e8cab3290a 100644 --- a/telephony/java/android/telephony/TelephonyManager.java +++ b/telephony/java/android/telephony/TelephonyManager.java @@ -177,7 +177,7 @@ public class TelephonyManager { /** * Returns the unique device ID, for example, the IMEI for GSM and the MEID - * for CDMA phones. Return null if device ID is not available. + * or ESN for CDMA phones. Return null if device ID is not available. * *

Requires Permission: * {@link android.Manifest.permission#READ_PHONE_STATE READ_PHONE_STATE} diff --git a/telephony/java/com/android/internal/telephony/cdma/CDMAPhone.java b/telephony/java/com/android/internal/telephony/cdma/CDMAPhone.java index 1f5accf38f21e..58dfeb985df19 100755 --- a/telephony/java/com/android/internal/telephony/cdma/CDMAPhone.java +++ b/telephony/java/com/android/internal/telephony/cdma/CDMAPhone.java @@ -430,9 +430,14 @@ public class CDMAPhone extends PhoneBase { return mMeid; } - //returns MEID in CDMA + //returns MEID or ESN in CDMA public String getDeviceId() { - return getMeid(); + String id = getMeid(); + if ((id == null) || id.matches("^0*$")) { + Log.d(LOG_TAG, "getDeviceId(): MEID is not initialized use ESN"); + id = getEsn(); + } + return id; } public String getDeviceSvn() { From be8e717ade0e0e3a68dba7fc2c0ea26a7209a08f Mon Sep 17 00:00:00 2001 From: Eric Rowe Date: Thu, 29 Jul 2010 12:11:29 -0700 Subject: [PATCH 05/10] Checkin initial bluetooth stress tests. Bluetooth stress tests include stress tests for enabling/disabling bluetooth, making the device discoverable/undiscoverable, and starting and stopping scans. Change-Id: Ic8ba09475ffe5551717438673e0ed3f4bd17cf2f --- core/tests/coretests/AndroidManifest.xml | 2 + .../bluetooth/BluetoothStressTest.java | 440 ++++++++++++++++++ 2 files changed, 442 insertions(+) create mode 100644 core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java diff --git a/core/tests/coretests/AndroidManifest.xml b/core/tests/coretests/AndroidManifest.xml index a77717fde8a64..036da9554d41c 100644 --- a/core/tests/coretests/AndroidManifest.xml +++ b/core/tests/coretests/AndroidManifest.xml @@ -36,6 +36,8 @@ android:description="@string/permdesc_testDenied" /> + + diff --git a/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java b/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java new file mode 100644 index 0000000000000..0fe83e1943787 --- /dev/null +++ b/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java @@ -0,0 +1,440 @@ +/* + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT 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.app.Instrumentation; +import android.bluetooth.BluetoothAdapter; +import android.content.BroadcastReceiver; +import android.content.Context; +import android.content.Intent; +import android.content.IntentFilter; +import android.test.InstrumentationTestCase; +import android.test.suitebuilder.annotation.LargeTest; +import android.util.Log; + +public class BluetoothStressTest extends InstrumentationTestCase { + private static final String TAG = "BluetoothEnablerStressTest"; + + /** + * Timeout for {@link BluetoothAdapter#disable()} in ms. + */ + private static final int DISABLE_TIMEOUT = 5000; + + /** + * Timeout for {@link BluetoothAdapter#enable()} in ms. + */ + private static final int ENABLE_TIMEOUT = 20000; + + /** + * Timeout for {@link BluetoothAdapter#setScanMode(int)} in ms. + */ + private static final int SET_SCAN_MODE_TIMEOUT = 5000; + + /** + * Timeout for {@link BluetoothAdapter#startDiscovery()} in ms. + */ + private static final int START_DISCOVERY_TIMEOUT = 5000; + + /** + * Timeout for {@link BluetoothAdapter#cancelDiscovery()} in ms. + */ + private static final int CANCEL_DISCOVERY_TIMEOUT = 5000; + + private static final int DISCOVERY_STARTED_FLAG = 1; + private static final int DISCOVERY_FINISHED_FLAG = 1 << 1; + private static final int SCAN_MODE_NONE_FLAG = 1 << 2; + private static final int SCAN_MODE_CONNECTABLE_FLAG = 1 << 3; + private static final int SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG = 1 << 4; + private static final int STATE_OFF_FLAG = 1 << 5; + private static final int STATE_TURNING_ON_FLAG = 1 << 6; + private static final int STATE_ON_FLAG = 1 << 7; + private static final int STATE_TURNING_OFF_FLAG = 1 << 8; + + /** + * Time between polls in ms. + */ + private static final int POLL_TIME = 100; + + private static final int ENABLE_ITERATIONS = 100; + private static final int DISCOVERABLE_ITERATIONS = 1000; + private static final int SCAN_ITERATIONS = 1000; + + private Context mContext; + + private Instrumentation mInstrumentation; + + private class BluetoothReceiver extends BroadcastReceiver { + private int mFiredFlags = 0; + + @Override + public void onReceive(Context context, Intent intent) { + synchronized (this) { + if (BluetoothAdapter.ACTION_DISCOVERY_STARTED.equals(intent.getAction())) { + mFiredFlags |= DISCOVERY_STARTED_FLAG; + } else if (BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(intent.getAction())) { + mFiredFlags |= DISCOVERY_FINISHED_FLAG; + } else if (BluetoothAdapter.ACTION_SCAN_MODE_CHANGED.equals(intent.getAction())) { + int mode = intent.getIntExtra(BluetoothAdapter.EXTRA_SCAN_MODE, + BluetoothAdapter.ERROR); + assertNotSame(mode, BluetoothAdapter.ERROR); + switch (mode) { + case BluetoothAdapter.SCAN_MODE_NONE: + mFiredFlags |= SCAN_MODE_NONE_FLAG; + break; + case BluetoothAdapter.SCAN_MODE_CONNECTABLE: + mFiredFlags |= SCAN_MODE_CONNECTABLE_FLAG; + break; + case BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE: + mFiredFlags |= SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG; + break; + } + } else if (BluetoothAdapter.ACTION_STATE_CHANGED.equals(intent.getAction())) { + int state = intent.getIntExtra(BluetoothAdapter.EXTRA_STATE, + BluetoothAdapter.ERROR); + assertNotSame(state, BluetoothAdapter.ERROR); + switch (state) { + case BluetoothAdapter.STATE_OFF: + mFiredFlags |= STATE_OFF_FLAG; + break; + case BluetoothAdapter.STATE_TURNING_ON: + mFiredFlags |= STATE_TURNING_ON_FLAG; + break; + case BluetoothAdapter.STATE_ON: + mFiredFlags |= STATE_ON_FLAG; + break; + case BluetoothAdapter.STATE_TURNING_OFF: + mFiredFlags |= STATE_TURNING_OFF_FLAG; + break; + } + } + } + } + + public int getFiredFlags() { + synchronized (this) { + return mFiredFlags; + } + } + + public void resetFiredFlags() { + synchronized (this) { + mFiredFlags = 0; + } + } + } + + private BluetoothReceiver mReceiver = new BluetoothReceiver(); + + @Override + protected void setUp() throws Exception { + super.setUp(); + + mInstrumentation = getInstrumentation(); + mContext = mInstrumentation.getTargetContext(); + + IntentFilter filter = new IntentFilter(); + filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_FINISHED); + filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_STARTED); + filter.addAction(BluetoothAdapter.ACTION_SCAN_MODE_CHANGED); + filter.addAction(BluetoothAdapter.ACTION_STATE_CHANGED); + mContext.registerReceiver(mReceiver, filter); + } + + @Override + protected void tearDown() throws Exception { + super.tearDown(); + + mContext.unregisterReceiver(mReceiver); + } + + @LargeTest + public void testEnableDisable() { + BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); + + for (int i = 0; i < ENABLE_ITERATIONS; i++) { + Log.i(TAG, "Enable iteration " + (i + 1) + " of " + ENABLE_ITERATIONS); + enable(adapter); + disable(adapter); + } + } + + @LargeTest + public void testDiscoverable() { + BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); + enable(adapter); + + for (int i = 0; i < DISCOVERABLE_ITERATIONS; i++) { + Log.i(TAG, "Discoverable iteration " + (i + 1) + " of " + DISCOVERABLE_ITERATIONS); + discoverable(adapter); + undiscoverable(adapter); + } + + disable(adapter); + } + + @LargeTest + public void testScan() { + BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); + enable(adapter); + + for (int i = 0; i < SCAN_ITERATIONS; i++) { + Log.i(TAG, "Scan iteration " + (i + 1) + " of " + SCAN_ITERATIONS); + startScan(adapter); + stopScan(adapter); + } + + disable(adapter); + } + + private void disable(BluetoothAdapter adapter) { + int mask = STATE_TURNING_OFF_FLAG | STATE_OFF_FLAG | SCAN_MODE_NONE_FLAG; + mReceiver.resetFiredFlags(); + + int state = adapter.getState(); + switch (state) { + case BluetoothAdapter.STATE_OFF: + assertFalse(adapter.isEnabled()); + return; + case BluetoothAdapter.STATE_ON: + assertTrue(adapter.isEnabled()); + assertTrue(adapter.disable()); + break; + case BluetoothAdapter.STATE_TURNING_ON: + assertFalse(adapter.isEnabled()); + assertTrue(adapter.disable()); + break; + case BluetoothAdapter.STATE_TURNING_OFF: + assertFalse(adapter.isEnabled()); + mask = 0; // Don't check for received intents since we might have missed them. + break; + default: + fail("disable() invalid state: " + state); + } + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < DISABLE_TIMEOUT) { + state = adapter.getState(); + if (state == BluetoothAdapter.STATE_OFF) { + assertFalse(adapter.isEnabled()); + if ((mReceiver.getFiredFlags() & mask) == mask) { + mReceiver.resetFiredFlags(); + return; + } + } else { + assertFalse(adapter.isEnabled()); + assertEquals(BluetoothAdapter.STATE_TURNING_OFF, state); + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail("disable() timeout: " + + "state=" + state + " (expected " + BluetoothAdapter.STATE_OFF + ") " + + "flags=" + firedFlags + " (expected " + mask + ")"); + } + + private void enable(BluetoothAdapter adapter) { + int mask = STATE_TURNING_ON_FLAG | STATE_ON_FLAG | SCAN_MODE_CONNECTABLE_FLAG; + mReceiver.resetFiredFlags(); + + int state = adapter.getState(); + switch (state) { + case BluetoothAdapter.STATE_ON: + assertTrue(adapter.isEnabled()); + return; + case BluetoothAdapter.STATE_OFF: + case BluetoothAdapter.STATE_TURNING_OFF: + assertFalse(adapter.isEnabled()); + assertTrue(adapter.enable()); + break; + case BluetoothAdapter.STATE_TURNING_ON: + assertFalse(adapter.isEnabled()); + mask = 0; // Don't check for received intents since we might have missed them. + break; + default: + fail("enable() invalid state: state=" + state); + } + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < ENABLE_TIMEOUT) { + state = adapter.getState(); + if (state == BluetoothAdapter.STATE_ON) { + assertTrue(adapter.isEnabled()); + if ((mReceiver.getFiredFlags() & mask) == mask) { + mReceiver.resetFiredFlags(); + return; + } + } else { + assertFalse(adapter.isEnabled()); + assertEquals(BluetoothAdapter.STATE_TURNING_ON, state); + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail("enable() timeout: " + + "state=" + state + " (expected " + BluetoothAdapter.STATE_OFF + ") " + + "flags=" + firedFlags + " (expected " + mask + ")"); + } + + private void discoverable(BluetoothAdapter adapter) { + int mask = SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG; + mReceiver.resetFiredFlags(); + + if (!adapter.isEnabled()) { + fail("discoverable() bluetooth not enabled"); + } + + int scanMode = adapter.getScanMode(); + if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) { + return; + } + + assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE); + assertTrue(adapter.setScanMode(BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE)); + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < SET_SCAN_MODE_TIMEOUT) { + scanMode = adapter.getScanMode(); + if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) { + if ((mReceiver.getFiredFlags() & mask) == mask) { + mReceiver.resetFiredFlags(); + return; + } + } else { + assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE); + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail("discoverable() timeout: " + + "scanMode=" + scanMode + " (expected " + + BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE + ") " + + "flags=" + firedFlags + " (expected " + mask + ")"); + } + + private void undiscoverable(BluetoothAdapter adapter) { + int mask = SCAN_MODE_CONNECTABLE_FLAG; + mReceiver.resetFiredFlags(); + + if (!adapter.isEnabled()) { + fail("undiscoverable(): bluetooth not enabled"); + } + + int scanMode = adapter.getScanMode(); + if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE) { + return; + } + + assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE); + assertTrue(adapter.setScanMode(BluetoothAdapter.SCAN_MODE_CONNECTABLE)); + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < SET_SCAN_MODE_TIMEOUT) { + scanMode = adapter.getScanMode(); + if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE) { + if ((mReceiver.getFiredFlags() & mask) == mask) { + mReceiver.resetFiredFlags(); + return; + } + } else { + assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE); + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail("undiscoverable() timeout: " + + "scanMode=" + scanMode + " (expected " + + BluetoothAdapter.SCAN_MODE_CONNECTABLE + ") " + + "flags=" + firedFlags + " (expected " + mask + ")"); + } + + private void startScan(BluetoothAdapter adapter) { + int mask = DISCOVERY_STARTED_FLAG; + mReceiver.resetFiredFlags(); + + if (!adapter.isEnabled()) { + fail("startScan(): bluetooth not enabled"); + } + + if (adapter.isDiscovering()) { + return; + } + + assertTrue(adapter.startDiscovery()); + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < START_DISCOVERY_TIMEOUT) { + if (adapter.isDiscovering() && ((mReceiver.getFiredFlags() & mask) == mask)) { + mReceiver.resetFiredFlags(); + return; + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail("startScan() timeout: " + + "isDiscovering=" + adapter.isDiscovering() + " " + + "flags=" + firedFlags + " (expected " + mask + ")"); + } + + private void stopScan(BluetoothAdapter adapter) { + int mask = DISCOVERY_FINISHED_FLAG; + mReceiver.resetFiredFlags(); + + if (!adapter.isEnabled()) { + fail("stopScan(): bluetooth not enabled"); + } + + if (!adapter.isDiscovering()) { + return; + } + + // TODO: put assertTrue() around cancelDiscovery() once it starts + // returning true. + adapter.cancelDiscovery(); + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < CANCEL_DISCOVERY_TIMEOUT) { + if (!adapter.isDiscovering() && ((mReceiver.getFiredFlags() & mask) == mask)) { + mReceiver.resetFiredFlags(); + return; + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail("stopScan() timeout: " + + "isDiscovering=" + adapter.isDiscovering() + " " + + "flags=" + firedFlags + " (expected " + mask + ")"); + } + + private void sleep(long time) { + try { + Thread.sleep(time); + } catch (InterruptedException e) { + } + } +} From 5247e3cd10b6e5fb19e22abbf3b904e79c7a0336 Mon Sep 17 00:00:00 2001 From: Eric Rowe Date: Mon, 9 Aug 2010 15:34:24 -0700 Subject: [PATCH 06/10] Remove @LargeTest annotations Change-Id: Ib7e6f6e8b6437db5ca2ad2bcb89f079a0cbf7453 --- .../src/android/bluetooth/BluetoothStressTest.java | 11 +++-------- 1 file changed, 3 insertions(+), 8 deletions(-) diff --git a/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java b/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java index 0fe83e1943787..cbd87140da33f 100644 --- a/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java +++ b/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java @@ -17,13 +17,11 @@ package android.bluetooth; import android.app.Instrumentation; -import android.bluetooth.BluetoothAdapter; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; import android.content.IntentFilter; import android.test.InstrumentationTestCase; -import android.test.suitebuilder.annotation.LargeTest; import android.util.Log; public class BluetoothStressTest extends InstrumentationTestCase { @@ -161,7 +159,6 @@ public class BluetoothStressTest extends InstrumentationTestCase { mContext.unregisterReceiver(mReceiver); } - @LargeTest public void testEnableDisable() { BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); @@ -172,7 +169,6 @@ public class BluetoothStressTest extends InstrumentationTestCase { } } - @LargeTest public void testDiscoverable() { BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); enable(adapter); @@ -186,7 +182,6 @@ public class BluetoothStressTest extends InstrumentationTestCase { disable(adapter); } - @LargeTest public void testScan() { BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); enable(adapter); @@ -336,7 +331,7 @@ public class BluetoothStressTest extends InstrumentationTestCase { mReceiver.resetFiredFlags(); if (!adapter.isEnabled()) { - fail("undiscoverable(): bluetooth not enabled"); + fail("undiscoverable() bluetooth not enabled"); } int scanMode = adapter.getScanMode(); @@ -374,7 +369,7 @@ public class BluetoothStressTest extends InstrumentationTestCase { mReceiver.resetFiredFlags(); if (!adapter.isEnabled()) { - fail("startScan(): bluetooth not enabled"); + fail("startScan() bluetooth not enabled"); } if (adapter.isDiscovering()) { @@ -404,7 +399,7 @@ public class BluetoothStressTest extends InstrumentationTestCase { mReceiver.resetFiredFlags(); if (!adapter.isEnabled()) { - fail("stopScan(): bluetooth not enabled"); + fail("stopScan() bluetooth not enabled"); } if (!adapter.isDiscovering()) { From 73debd1a55f98b93ec0919f89ef173725e9cb07a Mon Sep 17 00:00:00 2001 From: Eric Rowe Date: Thu, 26 Aug 2010 15:13:24 -0700 Subject: [PATCH 07/10] Improve logging and flexibility of BT stress tests. Change-Id: I657638b3b410175919da545e9a9b7d9df6466362 --- core/tests/coretests/AndroidManifest.xml | 12 +- .../bluetooth/BluetoothStressTest.java | 110 ++++++++++++------ .../bluetooth/BluetoothTestRunner.java | 73 ++++++++++++ 3 files changed, 158 insertions(+), 37 deletions(-) create mode 100644 core/tests/coretests/src/android/bluetooth/BluetoothTestRunner.java diff --git a/core/tests/coretests/AndroidManifest.xml b/core/tests/coretests/AndroidManifest.xml index 036da9554d41c..ce73ae1eb4334 100644 --- a/core/tests/coretests/AndroidManifest.xml +++ b/core/tests/coretests/AndroidManifest.xml @@ -1205,8 +1205,12 @@ - + + + + diff --git a/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java b/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java index cbd87140da33f..7a6ee8ecedf2d 100644 --- a/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java +++ b/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java @@ -16,16 +16,23 @@ package android.bluetooth; +import java.io.BufferedWriter; +import java.io.File; +import java.io.FileWriter; +import java.io.IOException; + import android.app.Instrumentation; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; import android.content.IntentFilter; +import android.os.Environment; import android.test.InstrumentationTestCase; import android.util.Log; public class BluetoothStressTest extends InstrumentationTestCase { - private static final String TAG = "BluetoothEnablerStressTest"; + private static final String TAG = "BluetoothStressTest"; + private static final String OUTPUT_FILE = "BluetoothStressTestOutput.txt"; /** * Timeout for {@link BluetoothAdapter#disable()} in ms. @@ -67,14 +74,12 @@ public class BluetoothStressTest extends InstrumentationTestCase { */ private static final int POLL_TIME = 100; - private static final int ENABLE_ITERATIONS = 100; - private static final int DISCOVERABLE_ITERATIONS = 1000; - private static final int SCAN_ITERATIONS = 1000; - private Context mContext; private Instrumentation mInstrumentation; + private BufferedWriter mOutputWriter; + private class BluetoothReceiver extends BroadcastReceiver { private int mFiredFlags = 0; @@ -144,6 +149,14 @@ public class BluetoothStressTest extends InstrumentationTestCase { mInstrumentation = getInstrumentation(); mContext = mInstrumentation.getTargetContext(); + try { + mOutputWriter = new BufferedWriter(new FileWriter(new File( + Environment.getExternalStorageDirectory(), OUTPUT_FILE), true)); + } catch (IOException e) { + Log.w(TAG, "Test output file could not be opened", e); + mOutputWriter = null; + } + IntentFilter filter = new IntentFilter(); filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_FINISHED); filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_STARTED); @@ -157,24 +170,34 @@ public class BluetoothStressTest extends InstrumentationTestCase { super.tearDown(); mContext.unregisterReceiver(mReceiver); + + if (mOutputWriter != null) { + try { + mOutputWriter.close(); + } catch (IOException e) { + Log.w(TAG, "Test output file could not be closed", e); + } + } } - public void testEnableDisable() { + public void testEnable() { + int iterations = BluetoothTestRunner.sEnableIterations; BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); - for (int i = 0; i < ENABLE_ITERATIONS; i++) { - Log.i(TAG, "Enable iteration " + (i + 1) + " of " + ENABLE_ITERATIONS); + for (int i = 0; i < iterations; i++) { + writeOutput("enable iteration " + (i + 1) + " of " + iterations); enable(adapter); disable(adapter); } } public void testDiscoverable() { + int iterations = BluetoothTestRunner.sDiscoverableIterations; BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); enable(adapter); - for (int i = 0; i < DISCOVERABLE_ITERATIONS; i++) { - Log.i(TAG, "Discoverable iteration " + (i + 1) + " of " + DISCOVERABLE_ITERATIONS); + for (int i = 0; i < iterations; i++) { + writeOutput("discoverable iteration " + (i + 1) + " of " + iterations); discoverable(adapter); undiscoverable(adapter); } @@ -183,11 +206,12 @@ public class BluetoothStressTest extends InstrumentationTestCase { } public void testScan() { + int iterations = BluetoothTestRunner.sScanIterations; BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); enable(adapter); - for (int i = 0; i < SCAN_ITERATIONS; i++) { - Log.i(TAG, "Scan iteration " + (i + 1) + " of " + SCAN_ITERATIONS); + for (int i = 0; i < iterations; i++) { + writeOutput("scan iteration " + (i + 1) + " of " + iterations); startScan(adapter); stopScan(adapter); } @@ -217,7 +241,7 @@ public class BluetoothStressTest extends InstrumentationTestCase { mask = 0; // Don't check for received intents since we might have missed them. break; default: - fail("disable() invalid state: " + state); + fail("disable() invalid state: state=" + state); } long s = System.currentTimeMillis(); @@ -227,6 +251,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { assertFalse(adapter.isEnabled()); if ((mReceiver.getFiredFlags() & mask) == mask) { mReceiver.resetFiredFlags(); + writeOutput(String.format("disable() completed in %d ms", + (System.currentTimeMillis() - s))); return; } } else { @@ -238,9 +264,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { int firedFlags = mReceiver.getFiredFlags(); mReceiver.resetFiredFlags(); - fail("disable() timeout: " + - "state=" + state + " (expected " + BluetoothAdapter.STATE_OFF + ") " + - "flags=" + firedFlags + " (expected " + mask + ")"); + fail(String.format("disable() timeout: state=%d (expected %d), flags=0x%x (expected 0x%x)", + state, BluetoothAdapter.STATE_OFF, firedFlags, mask)); } private void enable(BluetoothAdapter adapter) { @@ -272,6 +297,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { assertTrue(adapter.isEnabled()); if ((mReceiver.getFiredFlags() & mask) == mask) { mReceiver.resetFiredFlags(); + writeOutput(String.format("enable() completed in %d ms", + (System.currentTimeMillis() - s))); return; } } else { @@ -283,9 +310,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { int firedFlags = mReceiver.getFiredFlags(); mReceiver.resetFiredFlags(); - fail("enable() timeout: " + - "state=" + state + " (expected " + BluetoothAdapter.STATE_OFF + ") " + - "flags=" + firedFlags + " (expected " + mask + ")"); + fail(String.format("enable() timeout: state=%d (expected %d), flags=0x%x (expected 0x%x)", + state, BluetoothAdapter.STATE_ON, firedFlags, mask)); } private void discoverable(BluetoothAdapter adapter) { @@ -310,6 +336,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) { if ((mReceiver.getFiredFlags() & mask) == mask) { mReceiver.resetFiredFlags(); + writeOutput(String.format("discoverable() completed in %d ms", + (System.currentTimeMillis() - s))); return; } } else { @@ -320,10 +348,9 @@ public class BluetoothStressTest extends InstrumentationTestCase { int firedFlags = mReceiver.getFiredFlags(); mReceiver.resetFiredFlags(); - fail("discoverable() timeout: " + - "scanMode=" + scanMode + " (expected " + - BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE + ") " + - "flags=" + firedFlags + " (expected " + mask + ")"); + fail(String.format("discoverable() timeout: scanMode=%d (expected %d), flags=0x%x " + + "(expected 0x%x)", scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE, + firedFlags, mask)); } private void undiscoverable(BluetoothAdapter adapter) { @@ -348,6 +375,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE) { if ((mReceiver.getFiredFlags() & mask) == mask) { mReceiver.resetFiredFlags(); + writeOutput(String.format("undiscoverable() completed in %d ms", + (System.currentTimeMillis() - s))); return; } } else { @@ -358,10 +387,9 @@ public class BluetoothStressTest extends InstrumentationTestCase { int firedFlags = mReceiver.getFiredFlags(); mReceiver.resetFiredFlags(); - fail("undiscoverable() timeout: " + - "scanMode=" + scanMode + " (expected " + - BluetoothAdapter.SCAN_MODE_CONNECTABLE + ") " + - "flags=" + firedFlags + " (expected " + mask + ")"); + fail(String.format("undiscoverable() timeout: scanMode=%d (expected %d), flags=0x%x " + + "(expected 0x%x)", scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE, firedFlags, + mask)); } private void startScan(BluetoothAdapter adapter) { @@ -382,6 +410,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { while (System.currentTimeMillis() - s < START_DISCOVERY_TIMEOUT) { if (adapter.isDiscovering() && ((mReceiver.getFiredFlags() & mask) == mask)) { mReceiver.resetFiredFlags(); + writeOutput(String.format("startScan() completed in %d ms", + (System.currentTimeMillis() - s))); return; } sleep(POLL_TIME); @@ -389,9 +419,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { int firedFlags = mReceiver.getFiredFlags(); mReceiver.resetFiredFlags(); - fail("startScan() timeout: " + - "isDiscovering=" + adapter.isDiscovering() + " " + - "flags=" + firedFlags + " (expected " + mask + ")"); + fail(String.format("startScan() timeout: isDiscovering=%b, flags=0x%x (expected 0x%x)", + adapter.isDiscovering(), firedFlags, mask)); } private void stopScan(BluetoothAdapter adapter) { @@ -414,6 +443,8 @@ public class BluetoothStressTest extends InstrumentationTestCase { while (System.currentTimeMillis() - s < CANCEL_DISCOVERY_TIMEOUT) { if (!adapter.isDiscovering() && ((mReceiver.getFiredFlags() & mask) == mask)) { mReceiver.resetFiredFlags(); + writeOutput(String.format("stopScan() completed in %d ms", + (System.currentTimeMillis() - s))); return; } sleep(POLL_TIME); @@ -421,9 +452,22 @@ public class BluetoothStressTest extends InstrumentationTestCase { int firedFlags = mReceiver.getFiredFlags(); mReceiver.resetFiredFlags(); - fail("stopScan() timeout: " + - "isDiscovering=" + adapter.isDiscovering() + " " + - "flags=" + firedFlags + " (expected " + mask + ")"); + fail(String.format("stopScan() timeout: isDiscovering=%b, flags=0x%x (expected 0x%x)", + adapter.isDiscovering(), firedFlags, mask)); + + } + + private void writeOutput(String s) { + if (mOutputWriter == null) { + return; + } + try { + Log.i(TAG, s); + mOutputWriter.write(s + "\n"); + mOutputWriter.flush(); + } catch (IOException e) { + Log.w(TAG, "Could not write to output file", e); + } } private void sleep(long time) { diff --git a/core/tests/coretests/src/android/bluetooth/BluetoothTestRunner.java b/core/tests/coretests/src/android/bluetooth/BluetoothTestRunner.java new file mode 100644 index 0000000000000..cf0ff99d1283f --- /dev/null +++ b/core/tests/coretests/src/android/bluetooth/BluetoothTestRunner.java @@ -0,0 +1,73 @@ +/* + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT 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 junit.framework.TestSuite; + +import android.os.Bundle; +import android.test.InstrumentationTestRunner; +import android.test.InstrumentationTestSuite; + +public class BluetoothTestRunner extends InstrumentationTestRunner { + public static int sEnableIterations = 100; + public static int sDiscoverableIterations = 1000; + public static int sScanIterations = 1000; + + @Override + public TestSuite getAllTests() { + TestSuite suite = new InstrumentationTestSuite(this); + suite.addTestSuite(BluetoothStressTest.class); + return suite; + } + + @Override + public ClassLoader getLoader() { + return BluetoothTestRunner.class.getClassLoader(); + } + + @Override + public void onCreate(Bundle arguments) { + super.onCreate(arguments); + + String val = arguments.getString("enable_iterations"); + if (val != null) { + try { + sEnableIterations = Integer.parseInt(val); + } catch (NumberFormatException e) { + // Invalid argument, fall back to default value + } + } + + val = arguments.getString("discoverable_iterations"); + if (val != null) { + try { + sDiscoverableIterations = Integer.parseInt(val); + } catch (NumberFormatException e) { + // Invalid argument, fall back to default value + } + } + + val = arguments.getString("scan_iterations"); + if (val != null) { + try { + sScanIterations = Integer.parseInt(val); + } catch (NumberFormatException e) { + // Invalid argument, fall back to default value + } + } + } +} From 59d3b4920aca8ca32facdf5297de549539008533 Mon Sep 17 00:00:00 2001 From: Eric Rowe Date: Mon, 30 Aug 2010 16:14:08 -0700 Subject: [PATCH 08/10] DO NOT MERGE Separate utility methods into utility class. Methods in BluetoothTestUtils remain the same as they were in BluetoothStressTest except for the constructor and close(). The constructor is derived from setUp() and close() from tearDown(). Change-Id: I09f9637d3969c98e46cbde1d61bc6c3223aec7c1 --- .../bluetooth/BluetoothStressTest.java | 432 +---------------- .../android/bluetooth/BluetoothTestUtils.java | 441 ++++++++++++++++++ 2 files changed, 458 insertions(+), 415 deletions(-) create mode 100644 core/tests/coretests/src/android/bluetooth/BluetoothTestUtils.java diff --git a/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java b/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java index 7a6ee8ecedf2d..d8d9eba14dc31 100644 --- a/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java +++ b/core/tests/coretests/src/android/bluetooth/BluetoothStressTest.java @@ -16,168 +16,28 @@ package android.bluetooth; -import java.io.BufferedWriter; -import java.io.File; -import java.io.FileWriter; -import java.io.IOException; - -import android.app.Instrumentation; -import android.content.BroadcastReceiver; import android.content.Context; -import android.content.Intent; -import android.content.IntentFilter; -import android.os.Environment; import android.test.InstrumentationTestCase; -import android.util.Log; public class BluetoothStressTest extends InstrumentationTestCase { private static final String TAG = "BluetoothStressTest"; private static final String OUTPUT_FILE = "BluetoothStressTestOutput.txt"; - /** - * Timeout for {@link BluetoothAdapter#disable()} in ms. - */ - private static final int DISABLE_TIMEOUT = 5000; - - /** - * Timeout for {@link BluetoothAdapter#enable()} in ms. - */ - private static final int ENABLE_TIMEOUT = 20000; - - /** - * Timeout for {@link BluetoothAdapter#setScanMode(int)} in ms. - */ - private static final int SET_SCAN_MODE_TIMEOUT = 5000; - - /** - * Timeout for {@link BluetoothAdapter#startDiscovery()} in ms. - */ - private static final int START_DISCOVERY_TIMEOUT = 5000; - - /** - * Timeout for {@link BluetoothAdapter#cancelDiscovery()} in ms. - */ - private static final int CANCEL_DISCOVERY_TIMEOUT = 5000; - - private static final int DISCOVERY_STARTED_FLAG = 1; - private static final int DISCOVERY_FINISHED_FLAG = 1 << 1; - private static final int SCAN_MODE_NONE_FLAG = 1 << 2; - private static final int SCAN_MODE_CONNECTABLE_FLAG = 1 << 3; - private static final int SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG = 1 << 4; - private static final int STATE_OFF_FLAG = 1 << 5; - private static final int STATE_TURNING_ON_FLAG = 1 << 6; - private static final int STATE_ON_FLAG = 1 << 7; - private static final int STATE_TURNING_OFF_FLAG = 1 << 8; - - /** - * Time between polls in ms. - */ - private static final int POLL_TIME = 100; - - private Context mContext; - - private Instrumentation mInstrumentation; - - private BufferedWriter mOutputWriter; - - private class BluetoothReceiver extends BroadcastReceiver { - private int mFiredFlags = 0; - - @Override - public void onReceive(Context context, Intent intent) { - synchronized (this) { - if (BluetoothAdapter.ACTION_DISCOVERY_STARTED.equals(intent.getAction())) { - mFiredFlags |= DISCOVERY_STARTED_FLAG; - } else if (BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(intent.getAction())) { - mFiredFlags |= DISCOVERY_FINISHED_FLAG; - } else if (BluetoothAdapter.ACTION_SCAN_MODE_CHANGED.equals(intent.getAction())) { - int mode = intent.getIntExtra(BluetoothAdapter.EXTRA_SCAN_MODE, - BluetoothAdapter.ERROR); - assertNotSame(mode, BluetoothAdapter.ERROR); - switch (mode) { - case BluetoothAdapter.SCAN_MODE_NONE: - mFiredFlags |= SCAN_MODE_NONE_FLAG; - break; - case BluetoothAdapter.SCAN_MODE_CONNECTABLE: - mFiredFlags |= SCAN_MODE_CONNECTABLE_FLAG; - break; - case BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE: - mFiredFlags |= SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG; - break; - } - } else if (BluetoothAdapter.ACTION_STATE_CHANGED.equals(intent.getAction())) { - int state = intent.getIntExtra(BluetoothAdapter.EXTRA_STATE, - BluetoothAdapter.ERROR); - assertNotSame(state, BluetoothAdapter.ERROR); - switch (state) { - case BluetoothAdapter.STATE_OFF: - mFiredFlags |= STATE_OFF_FLAG; - break; - case BluetoothAdapter.STATE_TURNING_ON: - mFiredFlags |= STATE_TURNING_ON_FLAG; - break; - case BluetoothAdapter.STATE_ON: - mFiredFlags |= STATE_ON_FLAG; - break; - case BluetoothAdapter.STATE_TURNING_OFF: - mFiredFlags |= STATE_TURNING_OFF_FLAG; - break; - } - } - } - } - - public int getFiredFlags() { - synchronized (this) { - return mFiredFlags; - } - } - - public void resetFiredFlags() { - synchronized (this) { - mFiredFlags = 0; - } - } - } - - private BluetoothReceiver mReceiver = new BluetoothReceiver(); + private BluetoothTestUtils mTestUtils; @Override protected void setUp() throws Exception { super.setUp(); - mInstrumentation = getInstrumentation(); - mContext = mInstrumentation.getTargetContext(); - - try { - mOutputWriter = new BufferedWriter(new FileWriter(new File( - Environment.getExternalStorageDirectory(), OUTPUT_FILE), true)); - } catch (IOException e) { - Log.w(TAG, "Test output file could not be opened", e); - mOutputWriter = null; - } - - IntentFilter filter = new IntentFilter(); - filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_FINISHED); - filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_STARTED); - filter.addAction(BluetoothAdapter.ACTION_SCAN_MODE_CHANGED); - filter.addAction(BluetoothAdapter.ACTION_STATE_CHANGED); - mContext.registerReceiver(mReceiver, filter); + Context context = getInstrumentation().getTargetContext(); + mTestUtils = new BluetoothTestUtils(context, TAG, OUTPUT_FILE); } @Override protected void tearDown() throws Exception { super.tearDown(); - mContext.unregisterReceiver(mReceiver); - - if (mOutputWriter != null) { - try { - mOutputWriter.close(); - } catch (IOException e) { - Log.w(TAG, "Test output file could not be closed", e); - } - } + mTestUtils.close(); } public void testEnable() { @@ -185,295 +45,37 @@ public class BluetoothStressTest extends InstrumentationTestCase { BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); for (int i = 0; i < iterations; i++) { - writeOutput("enable iteration " + (i + 1) + " of " + iterations); - enable(adapter); - disable(adapter); + mTestUtils.writeOutput("enable iteration " + (i + 1) + " of " + iterations); + mTestUtils.enable(adapter); + mTestUtils.disable(adapter); } } public void testDiscoverable() { int iterations = BluetoothTestRunner.sDiscoverableIterations; BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); - enable(adapter); + mTestUtils.enable(adapter); for (int i = 0; i < iterations; i++) { - writeOutput("discoverable iteration " + (i + 1) + " of " + iterations); - discoverable(adapter); - undiscoverable(adapter); + mTestUtils.writeOutput("discoverable iteration " + (i + 1) + " of " + iterations); + mTestUtils.discoverable(adapter); + mTestUtils.undiscoverable(adapter); } - disable(adapter); + mTestUtils.disable(adapter); } public void testScan() { int iterations = BluetoothTestRunner.sScanIterations; BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); - enable(adapter); + mTestUtils.enable(adapter); for (int i = 0; i < iterations; i++) { - writeOutput("scan iteration " + (i + 1) + " of " + iterations); - startScan(adapter); - stopScan(adapter); + mTestUtils.writeOutput("scan iteration " + (i + 1) + " of " + iterations); + mTestUtils.startScan(adapter); + mTestUtils.stopScan(adapter); } - disable(adapter); - } - - private void disable(BluetoothAdapter adapter) { - int mask = STATE_TURNING_OFF_FLAG | STATE_OFF_FLAG | SCAN_MODE_NONE_FLAG; - mReceiver.resetFiredFlags(); - - int state = adapter.getState(); - switch (state) { - case BluetoothAdapter.STATE_OFF: - assertFalse(adapter.isEnabled()); - return; - case BluetoothAdapter.STATE_ON: - assertTrue(adapter.isEnabled()); - assertTrue(adapter.disable()); - break; - case BluetoothAdapter.STATE_TURNING_ON: - assertFalse(adapter.isEnabled()); - assertTrue(adapter.disable()); - break; - case BluetoothAdapter.STATE_TURNING_OFF: - assertFalse(adapter.isEnabled()); - mask = 0; // Don't check for received intents since we might have missed them. - break; - default: - fail("disable() invalid state: state=" + state); - } - - long s = System.currentTimeMillis(); - while (System.currentTimeMillis() - s < DISABLE_TIMEOUT) { - state = adapter.getState(); - if (state == BluetoothAdapter.STATE_OFF) { - assertFalse(adapter.isEnabled()); - if ((mReceiver.getFiredFlags() & mask) == mask) { - mReceiver.resetFiredFlags(); - writeOutput(String.format("disable() completed in %d ms", - (System.currentTimeMillis() - s))); - return; - } - } else { - assertFalse(adapter.isEnabled()); - assertEquals(BluetoothAdapter.STATE_TURNING_OFF, state); - } - sleep(POLL_TIME); - } - - int firedFlags = mReceiver.getFiredFlags(); - mReceiver.resetFiredFlags(); - fail(String.format("disable() timeout: state=%d (expected %d), flags=0x%x (expected 0x%x)", - state, BluetoothAdapter.STATE_OFF, firedFlags, mask)); - } - - private void enable(BluetoothAdapter adapter) { - int mask = STATE_TURNING_ON_FLAG | STATE_ON_FLAG | SCAN_MODE_CONNECTABLE_FLAG; - mReceiver.resetFiredFlags(); - - int state = adapter.getState(); - switch (state) { - case BluetoothAdapter.STATE_ON: - assertTrue(adapter.isEnabled()); - return; - case BluetoothAdapter.STATE_OFF: - case BluetoothAdapter.STATE_TURNING_OFF: - assertFalse(adapter.isEnabled()); - assertTrue(adapter.enable()); - break; - case BluetoothAdapter.STATE_TURNING_ON: - assertFalse(adapter.isEnabled()); - mask = 0; // Don't check for received intents since we might have missed them. - break; - default: - fail("enable() invalid state: state=" + state); - } - - long s = System.currentTimeMillis(); - while (System.currentTimeMillis() - s < ENABLE_TIMEOUT) { - state = adapter.getState(); - if (state == BluetoothAdapter.STATE_ON) { - assertTrue(adapter.isEnabled()); - if ((mReceiver.getFiredFlags() & mask) == mask) { - mReceiver.resetFiredFlags(); - writeOutput(String.format("enable() completed in %d ms", - (System.currentTimeMillis() - s))); - return; - } - } else { - assertFalse(adapter.isEnabled()); - assertEquals(BluetoothAdapter.STATE_TURNING_ON, state); - } - sleep(POLL_TIME); - } - - int firedFlags = mReceiver.getFiredFlags(); - mReceiver.resetFiredFlags(); - fail(String.format("enable() timeout: state=%d (expected %d), flags=0x%x (expected 0x%x)", - state, BluetoothAdapter.STATE_ON, firedFlags, mask)); - } - - private void discoverable(BluetoothAdapter adapter) { - int mask = SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG; - mReceiver.resetFiredFlags(); - - if (!adapter.isEnabled()) { - fail("discoverable() bluetooth not enabled"); - } - - int scanMode = adapter.getScanMode(); - if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) { - return; - } - - assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE); - assertTrue(adapter.setScanMode(BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE)); - - long s = System.currentTimeMillis(); - while (System.currentTimeMillis() - s < SET_SCAN_MODE_TIMEOUT) { - scanMode = adapter.getScanMode(); - if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) { - if ((mReceiver.getFiredFlags() & mask) == mask) { - mReceiver.resetFiredFlags(); - writeOutput(String.format("discoverable() completed in %d ms", - (System.currentTimeMillis() - s))); - return; - } - } else { - assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE); - } - sleep(POLL_TIME); - } - - int firedFlags = mReceiver.getFiredFlags(); - mReceiver.resetFiredFlags(); - fail(String.format("discoverable() timeout: scanMode=%d (expected %d), flags=0x%x " - + "(expected 0x%x)", scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE, - firedFlags, mask)); - } - - private void undiscoverable(BluetoothAdapter adapter) { - int mask = SCAN_MODE_CONNECTABLE_FLAG; - mReceiver.resetFiredFlags(); - - if (!adapter.isEnabled()) { - fail("undiscoverable() bluetooth not enabled"); - } - - int scanMode = adapter.getScanMode(); - if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE) { - return; - } - - assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE); - assertTrue(adapter.setScanMode(BluetoothAdapter.SCAN_MODE_CONNECTABLE)); - - long s = System.currentTimeMillis(); - while (System.currentTimeMillis() - s < SET_SCAN_MODE_TIMEOUT) { - scanMode = adapter.getScanMode(); - if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE) { - if ((mReceiver.getFiredFlags() & mask) == mask) { - mReceiver.resetFiredFlags(); - writeOutput(String.format("undiscoverable() completed in %d ms", - (System.currentTimeMillis() - s))); - return; - } - } else { - assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE); - } - sleep(POLL_TIME); - } - - int firedFlags = mReceiver.getFiredFlags(); - mReceiver.resetFiredFlags(); - fail(String.format("undiscoverable() timeout: scanMode=%d (expected %d), flags=0x%x " - + "(expected 0x%x)", scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE, firedFlags, - mask)); - } - - private void startScan(BluetoothAdapter adapter) { - int mask = DISCOVERY_STARTED_FLAG; - mReceiver.resetFiredFlags(); - - if (!adapter.isEnabled()) { - fail("startScan() bluetooth not enabled"); - } - - if (adapter.isDiscovering()) { - return; - } - - assertTrue(adapter.startDiscovery()); - - long s = System.currentTimeMillis(); - while (System.currentTimeMillis() - s < START_DISCOVERY_TIMEOUT) { - if (adapter.isDiscovering() && ((mReceiver.getFiredFlags() & mask) == mask)) { - mReceiver.resetFiredFlags(); - writeOutput(String.format("startScan() completed in %d ms", - (System.currentTimeMillis() - s))); - return; - } - sleep(POLL_TIME); - } - - int firedFlags = mReceiver.getFiredFlags(); - mReceiver.resetFiredFlags(); - fail(String.format("startScan() timeout: isDiscovering=%b, flags=0x%x (expected 0x%x)", - adapter.isDiscovering(), firedFlags, mask)); - } - - private void stopScan(BluetoothAdapter adapter) { - int mask = DISCOVERY_FINISHED_FLAG; - mReceiver.resetFiredFlags(); - - if (!adapter.isEnabled()) { - fail("stopScan() bluetooth not enabled"); - } - - if (!adapter.isDiscovering()) { - return; - } - - // TODO: put assertTrue() around cancelDiscovery() once it starts - // returning true. - adapter.cancelDiscovery(); - - long s = System.currentTimeMillis(); - while (System.currentTimeMillis() - s < CANCEL_DISCOVERY_TIMEOUT) { - if (!adapter.isDiscovering() && ((mReceiver.getFiredFlags() & mask) == mask)) { - mReceiver.resetFiredFlags(); - writeOutput(String.format("stopScan() completed in %d ms", - (System.currentTimeMillis() - s))); - return; - } - sleep(POLL_TIME); - } - - int firedFlags = mReceiver.getFiredFlags(); - mReceiver.resetFiredFlags(); - fail(String.format("stopScan() timeout: isDiscovering=%b, flags=0x%x (expected 0x%x)", - adapter.isDiscovering(), firedFlags, mask)); - - } - - private void writeOutput(String s) { - if (mOutputWriter == null) { - return; - } - try { - Log.i(TAG, s); - mOutputWriter.write(s + "\n"); - mOutputWriter.flush(); - } catch (IOException e) { - Log.w(TAG, "Could not write to output file", e); - } - } - - private void sleep(long time) { - try { - Thread.sleep(time); - } catch (InterruptedException e) { - } + mTestUtils.disable(adapter); } } diff --git a/core/tests/coretests/src/android/bluetooth/BluetoothTestUtils.java b/core/tests/coretests/src/android/bluetooth/BluetoothTestUtils.java new file mode 100644 index 0000000000000..82de5098e66be --- /dev/null +++ b/core/tests/coretests/src/android/bluetooth/BluetoothTestUtils.java @@ -0,0 +1,441 @@ +/* + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT 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.content.BroadcastReceiver; +import android.content.Context; +import android.content.Intent; +import android.content.IntentFilter; +import android.os.Environment; +import android.util.Log; + +import junit.framework.Assert; + +import java.io.BufferedWriter; +import java.io.File; +import java.io.FileWriter; +import java.io.IOException; + +public class BluetoothTestUtils extends Assert { + + /** + * Timeout for {@link BluetoothAdapter#disable()} in ms. + */ + private static final int DISABLE_TIMEOUT = 5000; + + /** + * Timeout for {@link BluetoothAdapter#enable()} in ms. + */ + private static final int ENABLE_TIMEOUT = 20000; + + /** + * Timeout for {@link BluetoothAdapter#setScanMode(int)} in ms. + */ + private static final int SET_SCAN_MODE_TIMEOUT = 5000; + + /** + * Timeout for {@link BluetoothAdapter#startDiscovery()} in ms. + */ + private static final int START_DISCOVERY_TIMEOUT = 5000; + + /** + * Timeout for {@link BluetoothAdapter#cancelDiscovery()} in ms. + */ + private static final int CANCEL_DISCOVERY_TIMEOUT = 5000; + + private static final int DISCOVERY_STARTED_FLAG = 1; + private static final int DISCOVERY_FINISHED_FLAG = 1 << 1; + private static final int SCAN_MODE_NONE_FLAG = 1 << 2; + private static final int SCAN_MODE_CONNECTABLE_FLAG = 1 << 3; + private static final int SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG = 1 << 4; + private static final int STATE_OFF_FLAG = 1 << 5; + private static final int STATE_TURNING_ON_FLAG = 1 << 6; + private static final int STATE_ON_FLAG = 1 << 7; + private static final int STATE_TURNING_OFF_FLAG = 1 << 8; + + /** + * Time between polls in ms. + */ + private static final int POLL_TIME = 100; + + private Context mContext; + + private BufferedWriter mOutputWriter; + + private String mOutputFile; + private String mTag; + + private class BluetoothReceiver extends BroadcastReceiver { + private int mFiredFlags = 0; + + @Override + public void onReceive(Context context, Intent intent) { + synchronized (this) { + if (BluetoothAdapter.ACTION_DISCOVERY_STARTED.equals(intent.getAction())) { + mFiredFlags |= DISCOVERY_STARTED_FLAG; + } else if (BluetoothAdapter.ACTION_DISCOVERY_FINISHED.equals(intent.getAction())) { + mFiredFlags |= DISCOVERY_FINISHED_FLAG; + } else if (BluetoothAdapter.ACTION_SCAN_MODE_CHANGED.equals(intent.getAction())) { + int mode = intent.getIntExtra(BluetoothAdapter.EXTRA_SCAN_MODE, + BluetoothAdapter.ERROR); + assertNotSame(mode, BluetoothAdapter.ERROR); + switch (mode) { + case BluetoothAdapter.SCAN_MODE_NONE: + mFiredFlags |= SCAN_MODE_NONE_FLAG; + break; + case BluetoothAdapter.SCAN_MODE_CONNECTABLE: + mFiredFlags |= SCAN_MODE_CONNECTABLE_FLAG; + break; + case BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE: + mFiredFlags |= SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG; + break; + } + } else if (BluetoothAdapter.ACTION_STATE_CHANGED.equals(intent.getAction())) { + int state = intent.getIntExtra(BluetoothAdapter.EXTRA_STATE, + BluetoothAdapter.ERROR); + assertNotSame(state, BluetoothAdapter.ERROR); + switch (state) { + case BluetoothAdapter.STATE_OFF: + mFiredFlags |= STATE_OFF_FLAG; + break; + case BluetoothAdapter.STATE_TURNING_ON: + mFiredFlags |= STATE_TURNING_ON_FLAG; + break; + case BluetoothAdapter.STATE_ON: + mFiredFlags |= STATE_ON_FLAG; + break; + case BluetoothAdapter.STATE_TURNING_OFF: + mFiredFlags |= STATE_TURNING_OFF_FLAG; + break; + } + } + } + } + + public int getFiredFlags() { + synchronized (this) { + return mFiredFlags; + } + } + + public void resetFiredFlags() { + synchronized (this) { + mFiredFlags = 0; + } + } + } + + private BluetoothReceiver mReceiver = new BluetoothReceiver(); + + public BluetoothTestUtils(Context context, String tag) { + this(context, tag, null); + } + + public BluetoothTestUtils(Context context, String tag, String outputFile) { + mContext = context; + mTag = tag; + mOutputFile = outputFile; + + if (mOutputFile == null) { + mOutputWriter = null; + } else { + try { + mOutputWriter = new BufferedWriter(new FileWriter(new File( + Environment.getExternalStorageDirectory(), mOutputFile), true)); + } catch (IOException e) { + Log.w(mTag, "Test output file could not be opened", e); + mOutputWriter = null; + } + } + + IntentFilter filter = new IntentFilter(); + filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_FINISHED); + filter.addAction(BluetoothAdapter.ACTION_DISCOVERY_STARTED); + filter.addAction(BluetoothAdapter.ACTION_SCAN_MODE_CHANGED); + filter.addAction(BluetoothAdapter.ACTION_STATE_CHANGED); + mContext.registerReceiver(mReceiver, filter); + } + + public void close() { + mContext.unregisterReceiver(mReceiver); + + if (mOutputWriter != null) { + try { + mOutputWriter.close(); + } catch (IOException e) { + Log.w(mTag, "Test output file could not be closed", e); + } + } + } + + public void enable(BluetoothAdapter adapter) { + int mask = STATE_TURNING_ON_FLAG | STATE_ON_FLAG | SCAN_MODE_CONNECTABLE_FLAG; + mReceiver.resetFiredFlags(); + + int state = adapter.getState(); + switch (state) { + case BluetoothAdapter.STATE_ON: + assertTrue(adapter.isEnabled()); + return; + case BluetoothAdapter.STATE_OFF: + case BluetoothAdapter.STATE_TURNING_OFF: + assertFalse(adapter.isEnabled()); + assertTrue(adapter.enable()); + break; + case BluetoothAdapter.STATE_TURNING_ON: + assertFalse(adapter.isEnabled()); + mask = 0; // Don't check for received intents since we might have missed them. + break; + default: + fail("enable() invalid state: state=" + state); + } + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < ENABLE_TIMEOUT) { + state = adapter.getState(); + if (state == BluetoothAdapter.STATE_ON) { + assertTrue(adapter.isEnabled()); + if ((mReceiver.getFiredFlags() & mask) == mask) { + mReceiver.resetFiredFlags(); + writeOutput(String.format("enable() completed in %d ms", + (System.currentTimeMillis() - s))); + return; + } + } else { + assertFalse(adapter.isEnabled()); + assertEquals(BluetoothAdapter.STATE_TURNING_ON, state); + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail(String.format("enable() timeout: state=%d (expected %d), flags=0x%x (expected 0x%x)", + state, BluetoothAdapter.STATE_ON, firedFlags, mask)); + } + + public void disable(BluetoothAdapter adapter) { + int mask = STATE_TURNING_OFF_FLAG | STATE_OFF_FLAG | SCAN_MODE_NONE_FLAG; + mReceiver.resetFiredFlags(); + + int state = adapter.getState(); + switch (state) { + case BluetoothAdapter.STATE_OFF: + assertFalse(adapter.isEnabled()); + return; + case BluetoothAdapter.STATE_ON: + assertTrue(adapter.isEnabled()); + assertTrue(adapter.disable()); + break; + case BluetoothAdapter.STATE_TURNING_ON: + assertFalse(adapter.isEnabled()); + assertTrue(adapter.disable()); + break; + case BluetoothAdapter.STATE_TURNING_OFF: + assertFalse(adapter.isEnabled()); + mask = 0; // Don't check for received intents since we might have missed them. + break; + default: + fail("disable() invalid state: state=" + state); + } + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < DISABLE_TIMEOUT) { + state = adapter.getState(); + if (state == BluetoothAdapter.STATE_OFF) { + assertFalse(adapter.isEnabled()); + if ((mReceiver.getFiredFlags() & mask) == mask) { + mReceiver.resetFiredFlags(); + writeOutput(String.format("disable() completed in %d ms", + (System.currentTimeMillis() - s))); + return; + } + } else { + assertFalse(adapter.isEnabled()); + assertEquals(BluetoothAdapter.STATE_TURNING_OFF, state); + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail(String.format("disable() timeout: state=%d (expected %d), flags=0x%x (expected 0x%x)", + state, BluetoothAdapter.STATE_OFF, firedFlags, mask)); + } + + public void discoverable(BluetoothAdapter adapter) { + int mask = SCAN_MODE_CONNECTABLE_DISCOVERABLE_FLAG; + mReceiver.resetFiredFlags(); + + if (!adapter.isEnabled()) { + fail("discoverable() bluetooth not enabled"); + } + + int scanMode = adapter.getScanMode(); + if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) { + return; + } + + assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE); + assertTrue(adapter.setScanMode(BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE)); + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < SET_SCAN_MODE_TIMEOUT) { + scanMode = adapter.getScanMode(); + if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE) { + if ((mReceiver.getFiredFlags() & mask) == mask) { + mReceiver.resetFiredFlags(); + writeOutput(String.format("discoverable() completed in %d ms", + (System.currentTimeMillis() - s))); + return; + } + } else { + assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE); + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail(String.format("discoverable() timeout: scanMode=%d (expected %d), flags=0x%x " + + "(expected 0x%x)", scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE, + firedFlags, mask)); + } + + public void undiscoverable(BluetoothAdapter adapter) { + int mask = SCAN_MODE_CONNECTABLE_FLAG; + mReceiver.resetFiredFlags(); + + if (!adapter.isEnabled()) { + fail("undiscoverable() bluetooth not enabled"); + } + + int scanMode = adapter.getScanMode(); + if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE) { + return; + } + + assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE); + assertTrue(adapter.setScanMode(BluetoothAdapter.SCAN_MODE_CONNECTABLE)); + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < SET_SCAN_MODE_TIMEOUT) { + scanMode = adapter.getScanMode(); + if (scanMode == BluetoothAdapter.SCAN_MODE_CONNECTABLE) { + if ((mReceiver.getFiredFlags() & mask) == mask) { + mReceiver.resetFiredFlags(); + writeOutput(String.format("undiscoverable() completed in %d ms", + (System.currentTimeMillis() - s))); + return; + } + } else { + assertEquals(scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE_DISCOVERABLE); + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail(String.format("undiscoverable() timeout: scanMode=%d (expected %d), flags=0x%x " + + "(expected 0x%x)", scanMode, BluetoothAdapter.SCAN_MODE_CONNECTABLE, firedFlags, + mask)); + } + + public void startScan(BluetoothAdapter adapter) { + int mask = DISCOVERY_STARTED_FLAG; + mReceiver.resetFiredFlags(); + + if (!adapter.isEnabled()) { + fail("startScan() bluetooth not enabled"); + } + + if (adapter.isDiscovering()) { + return; + } + + assertTrue(adapter.startDiscovery()); + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < START_DISCOVERY_TIMEOUT) { + if (adapter.isDiscovering() && ((mReceiver.getFiredFlags() & mask) == mask)) { + mReceiver.resetFiredFlags(); + writeOutput(String.format("startScan() completed in %d ms", + (System.currentTimeMillis() - s))); + return; + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail(String.format("startScan() timeout: isDiscovering=%b, flags=0x%x (expected 0x%x)", + adapter.isDiscovering(), firedFlags, mask)); + } + + public void stopScan(BluetoothAdapter adapter) { + int mask = DISCOVERY_FINISHED_FLAG; + mReceiver.resetFiredFlags(); + + if (!adapter.isEnabled()) { + fail("stopScan() bluetooth not enabled"); + } + + if (!adapter.isDiscovering()) { + return; + } + + // TODO: put assertTrue() around cancelDiscovery() once it starts returning true. + adapter.cancelDiscovery(); + + long s = System.currentTimeMillis(); + while (System.currentTimeMillis() - s < CANCEL_DISCOVERY_TIMEOUT) { + if (!adapter.isDiscovering() && ((mReceiver.getFiredFlags() & mask) == mask)) { + mReceiver.resetFiredFlags(); + writeOutput(String.format("stopScan() completed in %d ms", + (System.currentTimeMillis() - s))); + return; + } + sleep(POLL_TIME); + } + + int firedFlags = mReceiver.getFiredFlags(); + mReceiver.resetFiredFlags(); + fail(String.format("stopScan() timeout: isDiscovering=%b, flags=0x%x (expected 0x%x)", + adapter.isDiscovering(), firedFlags, mask)); + + } + + public void writeOutput(String s) { + Log.i(mTag, s); + if (mOutputWriter == null) { + return; + } + try { + mOutputWriter.write(s + "\n"); + mOutputWriter.flush(); + } catch (IOException e) { + Log.w(mTag, "Could not write to output file", e); + } + } + + private void sleep(long time) { + try { + Thread.sleep(time); + } catch (InterruptedException e) { + } + } +} From 6881e729155fab1ca7e6f84bcc789eaf90b9081a Mon Sep 17 00:00:00 2001 From: Eric Rowe Date: Tue, 31 Aug 2010 15:06:58 -0700 Subject: [PATCH 09/10] Add BT test instrumentation for reboot tests. Change-Id: If8134a1c11f3982086b7299e5c8bd3ef8eaa5959 --- .../bluetooth/BluetoothRebootStressTest.java | 94 +++++++++++++++++++ 1 file changed, 94 insertions(+) create mode 100644 core/tests/coretests/src/android/bluetooth/BluetoothRebootStressTest.java diff --git a/core/tests/coretests/src/android/bluetooth/BluetoothRebootStressTest.java b/core/tests/coretests/src/android/bluetooth/BluetoothRebootStressTest.java new file mode 100644 index 0000000000000..33e9dd7fabc6c --- /dev/null +++ b/core/tests/coretests/src/android/bluetooth/BluetoothRebootStressTest.java @@ -0,0 +1,94 @@ +/* + * Copyright (C) 2010 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT 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.content.Context; +import android.test.InstrumentationTestCase; + +/** + * Instrumentation test case for stress test involving rebooting the device. + *

+ * This test case tests that bluetooth is enabled after a device reboot. Because + * the device will reboot, the instrumentation must be driven by a script on the + * host side. + */ +public class BluetoothRebootStressTest extends InstrumentationTestCase { + private static final String TAG = "BluetoothRebootStressTest"; + private static final String OUTPUT_FILE = "BluetoothRebootStressTestOutput.txt"; + + private BluetoothTestUtils mTestUtils; + + @Override + protected void setUp() throws Exception { + super.setUp(); + + Context context = getInstrumentation().getTargetContext(); + mTestUtils = new BluetoothTestUtils(context, TAG, OUTPUT_FILE); + } + + @Override + protected void tearDown() throws Exception { + super.tearDown(); + + mTestUtils.close(); + } + + /** + * Test method used to start the test by turning bluetooth on. + */ + public void testStart() { + BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); + mTestUtils.enable(adapter); + } + + /** + * Test method used in the middle iterations of the test to check if + * bluetooth is on. Does not toggle bluetooth after the check. Assumes that + * bluetooth has been turned on by {@code #testStart()} + */ + public void testMiddleNoToggle() { + BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); + + assertTrue(adapter.isEnabled()); + } + + /** + * Test method used in the middle iterations of the test to check if + * bluetooth is on. Toggles bluetooth after the check. Assumes that + * bluetooth has been turned on by {@code #testStart()} + */ + public void testMiddleToggle() { + BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); + + assertTrue(adapter.isEnabled()); + + mTestUtils.disable(adapter); + mTestUtils.enable(adapter); + } + + /** + * Test method used in the stop the test by turning bluetooth off. Assumes + * that bluetooth has been turned on by {@code #testStart()} + */ + public void testStop() { + BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter(); + + assertTrue(adapter.isEnabled()); + + mTestUtils.disable(adapter); + } +} From ec721fd1db4d895b342cfb83c651e0b78afac4dd Mon Sep 17 00:00:00 2001 From: Leon Scroggins III Date: Tue, 14 Sep 2010 10:56:25 -0400 Subject: [PATCH 10/10] Add an option to hide the Voice Search icon. Some search engines do not support voice search, so provide a flag to disable showing the icon in the SearchDialog. Change-Id: I7ef4ad5d382edb86c08014260defa4af6d5eca0a --- core/java/android/app/SearchDialog.java | 4 +++- core/java/android/app/SearchManager.java | 8 ++++++++ 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/core/java/android/app/SearchDialog.java b/core/java/android/app/SearchDialog.java index 7625c04d61e23..cd22fa13e0151 100644 --- a/core/java/android/app/SearchDialog.java +++ b/core/java/android/app/SearchDialog.java @@ -588,7 +588,9 @@ public class SearchDialog extends Dialog implements OnItemClickListener, OnItemS */ private void updateVoiceButton(boolean empty) { int visibility = View.GONE; - if (mSearchable.getVoiceSearchEnabled() && empty) { + if ((mAppSearchData == null || !mAppSearchData.getBoolean( + SearchManager.DISABLE_VOICE_SEARCH, false)) + && mSearchable.getVoiceSearchEnabled() && empty) { Intent testIntent = null; if (mSearchable.getVoiceSearchLaunchWebSearch()) { testIntent = mVoiceWebSearchIntent; diff --git a/core/java/android/app/SearchManager.java b/core/java/android/app/SearchManager.java index a1ca707ab7b9c..2e9cd96f2695b 100644 --- a/core/java/android/app/SearchManager.java +++ b/core/java/android/app/SearchManager.java @@ -394,6 +394,14 @@ public class SearchManager */ public final static String CONTEXT_IS_VOICE = "android.search.CONTEXT_IS_VOICE"; + /** + * This means that the voice icon should not be shown at all, because the + * current search engine does not support voice search. + * @hide + */ + public final static String DISABLE_VOICE_SEARCH + = "android.search.DISABLE_VOICE_SEARCH"; + /** * Reference to the shared system search service. */