Commit 2b2775d5 authored by rockot@chromium.org's avatar rockot@chromium.org

Block some HID devices from chrome.hid.

This blacklists some specific types of HID devices from
being accessible to the chrome.hid API. Namely, any keyboard,
mice, other pointer devices, or system control inputs (such as
power and reset buttons) are blocked and cannot be enumerated
or opened by the consumers of the API.

BUG=355022
R=rpaquay

Review URL: https://codereview.chromium.org/258733002

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@266482 0039d316-1c4b-4281-b951-d872f2087c98
parent 9205af99
...@@ -11,6 +11,7 @@ ...@@ -11,6 +11,7 @@
#include "device/hid/hid_service.h" #include "device/hid/hid_service.h"
using device::HidService; using device::HidService;
using device::HidUsageAndPage;
namespace extensions { namespace extensions {
...@@ -44,7 +45,8 @@ scoped_ptr<base::ListValue> HidDeviceManager::GetApiDevices( ...@@ -44,7 +45,8 @@ scoped_ptr<base::ListValue> HidDeviceManager::GetApiDevices(
device::HidDeviceInfo device_info; device::HidDeviceInfo device_info;
if (hid_service->GetDeviceInfo(device_id, &device_info)) { if (hid_service->GetDeviceInfo(device_id, &device_info)) {
if (device_info.vendor_id == vendor_id && if (device_info.vendor_id == vendor_id &&
device_info.product_id == product_id) { device_info.product_id == product_id &&
IsDeviceAccessible(device_info)) {
api::hid::HidDeviceInfo api_device_info; api::hid::HidDeviceInfo api_device_info;
api_device_info.device_id = resource_id; api_device_info.device_id = resource_id;
api_device_info.vendor_id = device_info.vendor_id; api_device_info.vendor_id = device_info.vendor_id;
...@@ -114,4 +116,48 @@ void HidDeviceManager::UpdateDevices() { ...@@ -114,4 +116,48 @@ void HidDeviceManager::UpdateDevices() {
resource_ids_.swap(new_resource_ids); resource_ids_.swap(new_resource_ids);
} }
// static
// TODO(rockot): Add some tests for this.
bool HidDeviceManager::IsDeviceAccessible(
const device::HidDeviceInfo& device_info) {
for (std::vector<device::HidUsageAndPage>::const_iterator iter =
device_info.usages.begin();
iter != device_info.usages.end(); ++iter) {
if (!IsUsageAccessible(*iter)) {
return false;
}
}
return true;
}
// static
bool HidDeviceManager::IsUsageAccessible(
const HidUsageAndPage& usage_and_page) {
if (usage_and_page.usage_page == HidUsageAndPage::kPageKeyboard)
return false;
if (usage_and_page.usage_page != HidUsageAndPage::kPageGenericDesktop)
return true;
uint16_t usage = usage_and_page.usage;
if (usage == HidUsageAndPage::kGenericDesktopPointer ||
usage == HidUsageAndPage::kGenericDesktopMouse ||
usage == HidUsageAndPage::kGenericDesktopKeyboard ||
usage == HidUsageAndPage::kGenericDesktopKeypad) {
return false;
}
if (usage >= HidUsageAndPage::kGenericDesktopSystemControl &&
usage <= HidUsageAndPage::kGenericDesktopSystemWarmRestart) {
return false;
}
if (usage >= HidUsageAndPage::kGenericDesktopSystemDock &&
usage <= HidUsageAndPage::kGenericDesktopSystemDisplaySwap) {
return false;
}
return true;
}
} // namespace extensions } // namespace extensions
...@@ -44,6 +44,15 @@ class HidDeviceManager : public BrowserContextKeyedAPI { ...@@ -44,6 +44,15 @@ class HidDeviceManager : public BrowserContextKeyedAPI {
void UpdateDevices(); void UpdateDevices();
// Determines if a given device interface should be accessible to API
// consumers. In order for a device interface to be accessible, ALL of its
// specified usages must be accessible.
static bool IsDeviceAccessible(const device::HidDeviceInfo& device_info);
// Determines if a given usage is available to API consumers. This is used to
// blacklist usages which could be security or privacy concerns.
static bool IsUsageAccessible(const device::HidUsageAndPage& usage_and_page);
base::ThreadChecker thread_checker_; base::ThreadChecker thread_checker_;
int next_resource_id_; int next_resource_id_;
......
...@@ -46,6 +46,79 @@ struct HidUsageAndPage { ...@@ -46,6 +46,79 @@ struct HidUsageAndPage {
kPageMediaCenter = 0xFFBC kPageMediaCenter = 0xFFBC
}; };
// These usage enumerations are derived from the HID Usage Tables v1.11 spec.
enum GenericDesktopUsage {
kGenericDesktopUndefined = 0,
kGenericDesktopPointer = 1,
kGenericDesktopMouse = 2,
kGenericDesktopJoystick = 4,
kGenericDesktopGamePad = 5,
kGenericDesktopKeyboard = 6,
kGenericDesktopKeypad = 7,
kGenericDesktopMultiAxisController = 8,
kGenericDesktopX = 0x30,
kGenericDesktopY = 0x31,
kGenericDesktopZ = 0x32,
kGenericDesktopRx = 0x33,
kGenericDesktopRy = 0x34,
kGenericDesktopRz = 0x35,
kGenericDesktopSlider = 0x36,
kGenericDesktopDial = 0x37,
kGenericDesktopWheel = 0x38,
kGenericDesktopHatSwitch = 0x39,
kGenericDesktopCountedBuffer = 0x3a,
kGenericDesktopByteCount = 0x3b,
kGenericDesktopMotionWakeup = 0x3c,
kGenericDesktopStart = 0x3d,
kGenericDesktopSelect = 0x3e,
kGenericDesktopVx = 0x40,
kGenericDesktopVy = 0x41,
kGenericDesktopVz = 0x42,
kGenericDesktopVbrx = 0x43,
kGenericDesktopVbry = 0x44,
kGenericDesktopVbrz = 0x45,
kGenericDesktopVno = 0x46,
kGenericDesktopSystemControl = 0x80,
kGenericDesktopSystemPowerDown = 0x81,
kGenericDesktopSystemSleep = 0x82,
kGenericDesktopSystemWakeUp = 0x83,
kGenericDesktopSystemContextMenu = 0x84,
kGenericDesktopSystemMainMenu = 0x85,
kGenericDesktopSystemAppMenu = 0x86,
kGenericDesktopSystemMenuHelp = 0x87,
kGenericDesktopSystemMenuExit = 0x88,
kGenericDesktopSystemMenuSelect = 0x89,
kGenericDesktopSystemMenuRight = 0x8a,
kGenericDesktopSystemMenuLeft = 0x8b,
kGenericDesktopSystemMenuUp = 0x8c,
kGenericDesktopSystemMenuDown = 0x8d,
kGenericDesktopSystemColdRestart = 0x8e,
kGenericDesktopSystemWarmRestart = 0x8f,
kGenericDesktopDPadUp = 0x90,
kGenericDesktopDPadDown = 0x91,
kGenericDesktopDPadLeft = 0x92,
kGenericDesktopDPadRight = 0x93,
kGenericDesktopSystemDock = 0xa0,
kGenericDesktopSystemUndock = 0xa1,
kGenericDesktopSystemSetup = 0xa2,
kGenericDesktopSystemBreak = 0xa3,
kGenericDesktopSystemDebuggerBreak = 0xa4,
kGenericDesktopApplicationBreak = 0xa5,
kGenericDesktopApplicationDebuggerBreak = 0xa6,
kGenericDesktopSystemSpeakerMute = 0xa7,
kGenericDesktopSystemHibernate = 0xa8,
kGenericDesktopSystemDisplayInvert = 0xb0,
kGenericDesktopSystemDisplayInternal = 0xb1,
kGenericDesktopSystemDisplayExternal = 0xb2,
kGenericDesktopSystemDisplayBoth = 0xb3,
kGenericDesktopSystemDisplayDual = 0xb4,
kGenericDesktopSystemDisplayToggle = 0xb5,
kGenericDesktopSystemDisplaySwap = 0xb6,
};
HidUsageAndPage(uint16_t usage, Page usage_page) HidUsageAndPage(uint16_t usage, Page usage_page)
: usage(usage), usage_page(usage_page) {} : usage(usage), usage_page(usage_page) {}
~HidUsageAndPage() {} ~HidUsageAndPage() {}
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment