summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--core/java/android/bluetooth/BluetoothDevice.java12
-rw-r--r--core/java/android/server/BluetoothEventLoop.java4
-rw-r--r--core/jni/android_view_InputDevice.cpp4
-rw-r--r--include/androidfw/InputDevice.h15
-rw-r--r--libs/androidfw/InputDevice.cpp11
-rw-r--r--services/input/InputReader.cpp14
-rw-r--r--services/input/InputReader.h7
-rw-r--r--services/input/tests/InputReader_test.cpp12
-rw-r--r--services/java/com/android/server/SystemServer.java3
-rw-r--r--services/java/com/android/server/input/InputManagerService.java36
-rw-r--r--services/jni/com_android_server_input_InputManagerService.cpp39
11 files changed, 127 insertions, 30 deletions
diff --git a/core/java/android/bluetooth/BluetoothDevice.java b/core/java/android/bluetooth/BluetoothDevice.java
index 04af5f7..56e1735 100644
--- a/core/java/android/bluetooth/BluetoothDevice.java
+++ b/core/java/android/bluetooth/BluetoothDevice.java
@@ -160,6 +160,18 @@ public final class BluetoothDevice implements Parcelable {
"android.bluetooth.device.action.NAME_CHANGED";
/**
+ * Broadcast Action: Indicates the alias of a remote device has been
+ * changed.
+ * <p>Always contains the extra field {@link #EXTRA_DEVICE}.
+ * <p>Requires {@link android.Manifest.permission#BLUETOOTH} to receive.
+ *
+ * @hide
+ */
+ @SdkConstant(SdkConstantType.BROADCAST_INTENT_ACTION)
+ public static final String ACTION_ALIAS_CHANGED =
+ "android.bluetooth.device.action.ALIAS_CHANGED";
+
+ /**
* Broadcast Action: Indicates a change in the bond state of a remote
* device. For example, if a device is bonded (paired).
* <p>Always contains the extra fields {@link #EXTRA_DEVICE}, {@link
diff --git a/core/java/android/server/BluetoothEventLoop.java b/core/java/android/server/BluetoothEventLoop.java
index a2038c9..9c887a1 100644
--- a/core/java/android/server/BluetoothEventLoop.java
+++ b/core/java/android/server/BluetoothEventLoop.java
@@ -405,6 +405,10 @@ class BluetoothEventLoop {
mContext.sendBroadcast(intent, BLUETOOTH_PERM);
} else if (name.equals("Alias")) {
mBluetoothService.setRemoteDeviceProperty(address, name, propValues[1]);
+ Intent intent = new Intent(BluetoothDevice.ACTION_ALIAS_CHANGED);
+ intent.putExtra(BluetoothDevice.EXTRA_DEVICE, device);
+ intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
+ mContext.sendBroadcast(intent, BLUETOOTH_PERM);
} else if (name.equals("Class")) {
mBluetoothService.setRemoteDeviceProperty(address, name, propValues[1]);
Intent intent = new Intent(BluetoothDevice.ACTION_CLASS_CHANGED);
diff --git a/core/jni/android_view_InputDevice.cpp b/core/jni/android_view_InputDevice.cpp
index 5cb172b..d1f0a6a 100644
--- a/core/jni/android_view_InputDevice.cpp
+++ b/core/jni/android_view_InputDevice.cpp
@@ -35,13 +35,13 @@ static struct {
} gInputDeviceClassInfo;
jobject android_view_InputDevice_create(JNIEnv* env, const InputDeviceInfo& deviceInfo) {
- ScopedLocalRef<jstring> nameObj(env, env->NewStringUTF(deviceInfo.getName().string()));
+ ScopedLocalRef<jstring> nameObj(env, env->NewStringUTF(deviceInfo.getDisplayName().string()));
if (!nameObj.get()) {
return NULL;
}
ScopedLocalRef<jstring> descriptorObj(env,
- env->NewStringUTF(deviceInfo.getDescriptor().string()));
+ env->NewStringUTF(deviceInfo.getIdentifier().descriptor.string()));
if (!descriptorObj.get()) {
return NULL;
}
diff --git a/include/androidfw/InputDevice.h b/include/androidfw/InputDevice.h
index 38203af..d6ecbf0 100644
--- a/include/androidfw/InputDevice.h
+++ b/include/androidfw/InputDevice.h
@@ -66,13 +66,16 @@ public:
float fuzz;
};
- void initialize(int32_t id, int32_t generation,
- const String8& name, const String8& descriptor);
+ void initialize(int32_t id, int32_t generation, const InputDeviceIdentifier& identifier,
+ const String8& alias);
inline int32_t getId() const { return mId; }
inline int32_t getGeneration() const { return mGeneration; }
- inline const String8 getName() const { return mName; }
- inline const String8 getDescriptor() const { return mDescriptor; }
+ inline const InputDeviceIdentifier& getIdentifier() const { return mIdentifier; }
+ inline const String8& getAlias() const { return mAlias; }
+ inline const String8& getDisplayName() const {
+ return mAlias.isEmpty() ? mIdentifier.name : mAlias;
+ }
inline uint32_t getSources() const { return mSources; }
const MotionRange* getMotionRange(int32_t axis, uint32_t source) const;
@@ -103,8 +106,8 @@ public:
private:
int32_t mId;
int32_t mGeneration;
- String8 mName;
- String8 mDescriptor;
+ InputDeviceIdentifier mIdentifier;
+ String8 mAlias;
uint32_t mSources;
int32_t mKeyboardType;
sp<KeyCharacterMap> mKeyCharacterMap;
diff --git a/libs/androidfw/InputDevice.cpp b/libs/androidfw/InputDevice.cpp
index d6c49f7..5237063 100644
--- a/libs/androidfw/InputDevice.cpp
+++ b/libs/androidfw/InputDevice.cpp
@@ -127,12 +127,11 @@ String8 getInputDeviceConfigurationFilePathByName(
// --- InputDeviceInfo ---
InputDeviceInfo::InputDeviceInfo() {
- initialize(-1, -1, String8("uninitialized device info"), String8("unknown"));
+ initialize(-1, -1, InputDeviceIdentifier(), String8());
}
InputDeviceInfo::InputDeviceInfo(const InputDeviceInfo& other) :
- mId(other.mId), mGeneration(other.mGeneration),
- mName(other.mName), mDescriptor(other.mDescriptor),
+ mId(other.mId), mGeneration(other.mGeneration), mIdentifier(other.mIdentifier),
mSources(other.mSources),
mKeyboardType(other.mKeyboardType),
mKeyCharacterMap(other.mKeyCharacterMap),
@@ -144,11 +143,11 @@ InputDeviceInfo::~InputDeviceInfo() {
}
void InputDeviceInfo::initialize(int32_t id, int32_t generation,
- const String8& name, const String8& descriptor) {
+ const InputDeviceIdentifier& identifier, const String8& alias) {
mId = id;
mGeneration = generation;
- mName = name;
- mDescriptor = descriptor;
+ mIdentifier = identifier;
+ mAlias = alias;
mSources = 0;
mKeyboardType = AINPUT_KEYBOARD_TYPE_NONE;
mHasVibrator = false;
diff --git a/services/input/InputReader.cpp b/services/input/InputReader.cpp
index 3a48b16..6022f10 100644
--- a/services/input/InputReader.cpp
+++ b/services/input/InputReader.cpp
@@ -918,7 +918,7 @@ void InputDevice::dump(String8& dump) {
getDeviceInfo(& deviceInfo);
dump.appendFormat(INDENT "Device %d: %s\n", deviceInfo.getId(),
- deviceInfo.getName().string());
+ deviceInfo.getDisplayName().string());
dump.appendFormat(INDENT2 "Generation: %d\n", mGeneration);
dump.appendFormat(INDENT2 "IsExternal: %s\n", toString(mIsExternal));
dump.appendFormat(INDENT2 "Sources: 0x%08x\n", deviceInfo.getSources());
@@ -972,6 +972,16 @@ void InputDevice::configure(nsecs_t when, const InputReaderConfiguration* config
}
}
+ if (!changes || (changes & InputReaderConfiguration::CHANGE_DEVICE_ALIAS)) {
+ if (!(mClasses & INPUT_DEVICE_CLASS_VIRTUAL)) {
+ String8 alias = mContext->getPolicy()->getDeviceAlias(mIdentifier);
+ if (mAlias != alias) {
+ mAlias = alias;
+ bumpGeneration();
+ }
+ }
+ }
+
size_t numMappers = mMappers.size();
for (size_t i = 0; i < numMappers; i++) {
InputMapper* mapper = mMappers[i];
@@ -1039,7 +1049,7 @@ void InputDevice::timeoutExpired(nsecs_t when) {
}
void InputDevice::getDeviceInfo(InputDeviceInfo* outDeviceInfo) {
- outDeviceInfo->initialize(mId, mGeneration, mIdentifier.name, mIdentifier.descriptor);
+ outDeviceInfo->initialize(mId, mGeneration, mIdentifier, mAlias);
size_t numMappers = mMappers.size();
for (size_t i = 0; i < numMappers; i++) {
diff --git a/services/input/InputReader.h b/services/input/InputReader.h
index acdec85..8257dbc 100644
--- a/services/input/InputReader.h
+++ b/services/input/InputReader.h
@@ -70,6 +70,9 @@ struct InputReaderConfiguration {
// The keyboard layouts must be reloaded.
CHANGE_KEYBOARD_LAYOUTS = 1 << 4,
+ // The device name alias supplied by the may have changed for some devices.
+ CHANGE_DEVICE_ALIAS = 1 << 5,
+
// All devices must be reopened.
CHANGE_MUST_REOPEN = 1 << 31,
};
@@ -228,6 +231,9 @@ public:
/* Gets the keyboard layout for a particular input device. */
virtual sp<KeyCharacterMap> getKeyboardLayoutOverlay(const String8& inputDeviceDescriptor) = 0;
+
+ /* Gets a user-supplied alias for a particular input device, or an empty string if none. */
+ virtual String8 getDeviceAlias(const InputDeviceIdentifier& identifier) = 0;
};
@@ -528,6 +534,7 @@ private:
int32_t mId;
int32_t mGeneration;
InputDeviceIdentifier mIdentifier;
+ String8 mAlias;
uint32_t mClasses;
Vector<InputMapper*> mMappers;
diff --git a/services/input/tests/InputReader_test.cpp b/services/input/tests/InputReader_test.cpp
index a4b7585..0f755ae 100644
--- a/services/input/tests/InputReader_test.cpp
+++ b/services/input/tests/InputReader_test.cpp
@@ -174,6 +174,10 @@ private:
virtual sp<KeyCharacterMap> getKeyboardLayoutOverlay(const String8& inputDeviceDescriptor) {
return NULL;
}
+
+ virtual String8 getDeviceAlias(const InputDeviceIdentifier& identifier) {
+ return String8::empty();
+ }
};
@@ -1081,7 +1085,7 @@ TEST_F(InputReaderTest, GetInputDevices) {
ASSERT_EQ(1U, inputDevices.size());
ASSERT_EQ(1, inputDevices[0].getId());
- ASSERT_STREQ("keyboard", inputDevices[0].getName().string());
+ ASSERT_STREQ("keyboard", inputDevices[0].getIdentifier().name.string());
ASSERT_EQ(AINPUT_KEYBOARD_TYPE_NON_ALPHABETIC, inputDevices[0].getKeyboardType());
ASSERT_EQ(AINPUT_SOURCE_KEYBOARD, inputDevices[0].getSources());
ASSERT_EQ(size_t(0), inputDevices[0].getMotionRanges().size());
@@ -1090,7 +1094,7 @@ TEST_F(InputReaderTest, GetInputDevices) {
inputDevices = mFakePolicy->getInputDevices();
ASSERT_EQ(1U, inputDevices.size());
ASSERT_EQ(1, inputDevices[0].getId());
- ASSERT_STREQ("keyboard", inputDevices[0].getName().string());
+ ASSERT_STREQ("keyboard", inputDevices[0].getIdentifier().name.string());
ASSERT_EQ(AINPUT_KEYBOARD_TYPE_NON_ALPHABETIC, inputDevices[0].getKeyboardType());
ASSERT_EQ(AINPUT_SOURCE_KEYBOARD, inputDevices[0].getSources());
ASSERT_EQ(size_t(0), inputDevices[0].getMotionRanges().size());
@@ -1311,7 +1315,7 @@ TEST_F(InputDeviceTest, WhenNoMappersAreRegistered_DeviceIsIgnored) {
InputDeviceInfo info;
mDevice->getDeviceInfo(&info);
ASSERT_EQ(DEVICE_ID, info.getId());
- ASSERT_STREQ(DEVICE_NAME, info.getName().string());
+ ASSERT_STREQ(DEVICE_NAME, info.getIdentifier().name.string());
ASSERT_EQ(AINPUT_KEYBOARD_TYPE_NONE, info.getKeyboardType());
ASSERT_EQ(AINPUT_SOURCE_UNKNOWN, info.getSources());
@@ -1381,7 +1385,7 @@ TEST_F(InputDeviceTest, WhenMappersAreRegistered_DeviceIsNotIgnoredAndForwardsRe
InputDeviceInfo info;
mDevice->getDeviceInfo(&info);
ASSERT_EQ(DEVICE_ID, info.getId());
- ASSERT_STREQ(DEVICE_NAME, info.getName().string());
+ ASSERT_STREQ(DEVICE_NAME, info.getIdentifier().name.string());
ASSERT_EQ(AINPUT_KEYBOARD_TYPE_ALPHABETIC, info.getKeyboardType());
ASSERT_EQ(uint32_t(AINPUT_SOURCE_KEYBOARD | AINPUT_SOURCE_TOUCHSCREEN), info.getSources());
diff --git a/services/java/com/android/server/SystemServer.java b/services/java/com/android/server/SystemServer.java
index 02c4d5a..729c3f3 100644
--- a/services/java/com/android/server/SystemServer.java
+++ b/services/java/com/android/server/SystemServer.java
@@ -726,6 +726,7 @@ class ServerThread extends Thread {
final StatusBarManagerService statusBarF = statusBar;
final DreamManagerService dreamyF = dreamy;
final InputManagerService inputManagerF = inputManager;
+ final BluetoothService bluetoothF = bluetooth;
// We now tell the activity manager it is okay to run third party
// code. It will call back into us once it has gotten to the state
@@ -838,7 +839,7 @@ class ServerThread extends Thread {
reportWtf("making DreamManagerService ready", e);
}
try {
- if (inputManagerF != null) inputManagerF.systemReady();
+ if (inputManagerF != null) inputManagerF.systemReady(bluetoothF);
} catch (Throwable e) {
reportWtf("making InputManagerService ready", e);
}
diff --git a/services/java/com/android/server/input/InputManagerService.java b/services/java/com/android/server/input/InputManagerService.java
index a4ed31c..189a9c7 100644
--- a/services/java/com/android/server/input/InputManagerService.java
+++ b/services/java/com/android/server/input/InputManagerService.java
@@ -26,6 +26,8 @@ import org.xmlpull.v1.XmlPullParserException;
import org.xmlpull.v1.XmlSerializer;
import android.Manifest;
+import android.bluetooth.BluetoothAdapter;
+import android.bluetooth.BluetoothDevice;
import android.content.BroadcastReceiver;
import android.content.ComponentName;
import android.content.Context;
@@ -56,6 +58,7 @@ import android.os.Process;
import android.os.RemoteException;
import android.provider.Settings;
import android.provider.Settings.SettingNotFoundException;
+import android.server.BluetoothService;
import android.util.Log;
import android.util.Slog;
import android.util.SparseArray;
@@ -106,6 +109,7 @@ public class InputManagerService extends IInputManager.Stub implements Watchdog.
private final Callbacks mCallbacks;
private final InputManagerHandler mHandler;
private boolean mSystemReady;
+ private BluetoothService mBluetoothService;
// Persistent data store. Must be locked each time during use.
private final PersistentDataStore mDataStore = new PersistentDataStore();
@@ -167,6 +171,7 @@ public class InputManagerService extends IInputManager.Stub implements Watchdog.
int repeat, int token);
private static native void nativeCancelVibrate(int ptr, int deviceId, int token);
private static native void nativeReloadKeyboardLayouts(int ptr);
+ private static native void nativeReloadDeviceAliases(int ptr);
private static native String nativeDump(int ptr);
private static native void nativeMonitor(int ptr);
@@ -217,12 +222,12 @@ public class InputManagerService extends IInputManager.Stub implements Watchdog.
updateShowTouchesFromSettings();
}
- public void systemReady() {
+ public void systemReady(BluetoothService bluetoothService) {
if (DEBUG) {
Slog.d(TAG, "System ready.");
}
+ mBluetoothService = bluetoothService;
mSystemReady = true;
- reloadKeyboardLayouts();
IntentFilter filter = new IntentFilter(Intent.ACTION_PACKAGE_ADDED);
filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
@@ -237,12 +242,30 @@ public class InputManagerService extends IInputManager.Stub implements Watchdog.
reloadKeyboardLayouts();
}
}, filter, null, mHandler);
+
+ filter = new IntentFilter(BluetoothDevice.ACTION_ALIAS_CHANGED);
+ mContext.registerReceiver(new BroadcastReceiver() {
+ @Override
+ public void onReceive(Context context, Intent intent) {
+ if (DEBUG) {
+ Slog.d(TAG, "Bluetooth alias changed, reloading device names.");
+ }
+ reloadDeviceAliases();
+ }
+ }, filter, null, mHandler);
+
+ reloadKeyboardLayouts();
+ reloadDeviceAliases();
}
private void reloadKeyboardLayouts() {
nativeReloadKeyboardLayouts(mPtr);
}
+ private void reloadDeviceAliases() {
+ nativeReloadDeviceAliases(mPtr);
+ }
+
public void setDisplaySize(int displayId, int width, int height,
int externalWidth, int externalHeight) {
if (width <= 0 || height <= 0 || externalWidth <= 0 || externalHeight <= 0) {
@@ -1121,6 +1144,15 @@ public class InputManagerService extends IInputManager.Stub implements Watchdog.
return result;
}
+ // Native callback.
+ private String getDeviceAlias(String uniqueId) {
+ if (mBluetoothService != null &&
+ BluetoothAdapter.checkBluetoothAddress(uniqueId)) {
+ return mBluetoothService.getRemoteAlias(uniqueId);
+ }
+ return null;
+ }
+
/**
* Callback interface implemented by the Window Manager.
diff --git a/services/jni/com_android_server_input_InputManagerService.cpp b/services/jni/com_android_server_input_InputManagerService.cpp
index b361a26..b2a2429 100644
--- a/services/jni/com_android_server_input_InputManagerService.cpp
+++ b/services/jni/com_android_server_input_InputManagerService.cpp
@@ -83,6 +83,7 @@ static struct {
jmethodID getPointerLayer;
jmethodID getPointerIcon;
jmethodID getKeyboardLayoutOverlay;
+ jmethodID getDeviceAlias;
} gServiceClassInfo;
static struct {
@@ -183,7 +184,6 @@ public:
void setSystemUiVisibility(int32_t visibility);
void setPointerSpeed(int32_t speed);
void setShowTouches(bool enabled);
- void reloadKeyboardLayouts();
/* --- InputReaderPolicyInterface implementation --- */
@@ -191,6 +191,7 @@ public:
virtual sp<PointerControllerInterface> obtainPointerController(int32_t deviceId);
virtual void notifyInputDevicesChanged(const Vector<InputDeviceInfo>& inputDevices);
virtual sp<KeyCharacterMap> getKeyboardLayoutOverlay(const String8& inputDeviceDescriptor);
+ virtual String8 getDeviceAlias(const InputDeviceIdentifier& identifier);
/* --- InputDispatcherPolicyInterface implementation --- */
@@ -551,6 +552,21 @@ sp<KeyCharacterMap> NativeInputManager::getKeyboardLayoutOverlay(
return result;
}
+String8 NativeInputManager::getDeviceAlias(const InputDeviceIdentifier& identifier) {
+ JNIEnv* env = jniEnv();
+
+ ScopedLocalRef<jstring> uniqueIdObj(env, env->NewStringUTF(identifier.uniqueId.string()));
+ ScopedLocalRef<jstring> aliasObj(env, jstring(env->CallObjectMethod(mServiceObj,
+ gServiceClassInfo.getDeviceAlias, uniqueIdObj.get())));
+ String8 result;
+ if (aliasObj.get()) {
+ ScopedUtfChars aliasChars(env, aliasObj.get());
+ result.setTo(aliasChars.c_str());
+ }
+ checkAndClearExceptionFromCallback(env, "getDeviceAlias");
+ return result;
+}
+
void NativeInputManager::notifySwitch(nsecs_t when, int32_t switchCode,
int32_t switchValue, uint32_t policyFlags) {
#if DEBUG_INPUT_DISPATCHER_POLICY
@@ -757,11 +773,6 @@ void NativeInputManager::setShowTouches(bool enabled) {
InputReaderConfiguration::CHANGE_SHOW_TOUCHES);
}
-void NativeInputManager::reloadKeyboardLayouts() {
- mInputManager->getReader()->requestRefreshConfiguration(
- InputReaderConfiguration::CHANGE_KEYBOARD_LAYOUTS);
-}
-
bool NativeInputManager::isScreenOn() {
return android_server_PowerManagerService_isScreenOn();
}
@@ -1296,7 +1307,16 @@ static void nativeReloadKeyboardLayouts(JNIEnv* env,
jclass clazz, jint ptr) {
NativeInputManager* im = reinterpret_cast<NativeInputManager*>(ptr);
- im->reloadKeyboardLayouts();
+ im->getInputManager()->getReader()->requestRefreshConfiguration(
+ InputReaderConfiguration::CHANGE_KEYBOARD_LAYOUTS);
+}
+
+static void nativeReloadDeviceAliases(JNIEnv* env,
+ jclass clazz, jint ptr) {
+ NativeInputManager* im = reinterpret_cast<NativeInputManager*>(ptr);
+
+ im->getInputManager()->getReader()->requestRefreshConfiguration(
+ InputReaderConfiguration::CHANGE_DEVICE_ALIAS);
}
static jstring nativeDump(JNIEnv* env, jclass clazz, jint ptr) {
@@ -1366,6 +1386,8 @@ static JNINativeMethod gInputManagerMethods[] = {
(void*) nativeCancelVibrate },
{ "nativeReloadKeyboardLayouts", "(I)V",
(void*) nativeReloadKeyboardLayouts },
+ { "nativeReloadDeviceAliases", "(I)V",
+ (void*) nativeReloadDeviceAliases },
{ "nativeDump", "(I)Ljava/lang/String;",
(void*) nativeDump },
{ "nativeMonitor", "(I)V",
@@ -1464,6 +1486,9 @@ int register_android_server_InputManager(JNIEnv* env) {
GET_METHOD_ID(gServiceClassInfo.getKeyboardLayoutOverlay, clazz,
"getKeyboardLayoutOverlay", "(Ljava/lang/String;)[Ljava/lang/String;");
+ GET_METHOD_ID(gServiceClassInfo.getDeviceAlias, clazz,
+ "getDeviceAlias", "(Ljava/lang/String;)Ljava/lang/String;");
+
// InputDevice
FIND_CLASS(gInputDeviceClassInfo.clazz, "android/view/InputDevice");