#include <IOKit/IOLib.h>
#include <IOKit/assert.h>
#include <IOKit/hidsystem/IOHIDUsageTables.h>
#include <IOKit/hidsystem/IOHIDParameter.h>
#include <IOKit/hidsystem/IOHIDShared.h>
#include <IOKit/usb/USB.h>
#include "IOHIDKeyboard.h"
#include "IOHIDKeys.h"
#include "IOHIDElement.h"
#define kFnModifierUsagePageKey "FnModifierUsagePage"
#define kFnModifierUsageKey "FnModifierUsage"
#define kFnSpecialKeyMapKey "FnSpecialKeyMap"
#define kFnNonSpecialUsageMapKey "FnNonSpecialUsageMap"
#define kNumPadUsageMapKey "NumPadUsageMap"
#define super IOHIKeyboard
OSDefineMetaClassAndStructors(IOHIDKeyboard, IOHIKeyboard)
extern unsigned char hid_usb_2_adb_keymap[];
IOHIDKeyboard *
IOHIDKeyboard::Keyboard(OSArray *elements, IOHIDDevice *owner)
{
IOHIDKeyboard *keyboard = new IOHIDKeyboard;
if ((keyboard == 0) || !keyboard->init() ||
!keyboard->findDesiredElements(elements, owner))
{
if (keyboard) keyboard->release();
return 0;
}
return keyboard;
}
bool
IOHIDKeyboard::init(OSDictionary *properties)
{
if (!super::init(properties)) return false;
_oldmodifier = 0;
_asyncLEDThread = 0;
_ledState = 0;
_fKeyMode = 0;
_lastFKeyValue = 0;
_numLeds = 0;
_consumer = 0;
_publishNotify = 0;
_stickyKeysOn = false;
_vendorID = 0;
_productID = 0;
_locationID = 0;
_transport = 0;
_keyboardLock = IORecursiveLockAlloc();
_keyCodeArrayValuePtrArray = 0;
_ledCookies[0] = -1;
_ledCookies[1] = -1;
bzero(_modifierValuePtrs, sizeof(UInt32*)*8);
bzero(_ledValuePtrs, sizeof(UInt32*)*2);
bzero(_secondaryKeys, sizeof(SecondaryKey)*255);
_fKeyValuePtr = 0;
bcopy(hid_usb_2_adb_keymap, _usb_2_adb_keymap, ADB_CONVERTER_LEN);
return true;
}
bool
IOHIDKeyboard::start(IOService *provider)
{
OSNumber *xml_swap_CTRL_CAPSLOCK;
OSNumber *xml_swap_CMD_ALT;
UInt16 productIDVal;
UInt16 vendorIDVal;
_provider = provider;
_transport = OSDynamicCast(OSString,provider->getProperty(kIOHIDTransportKey));
_vendorID = OSDynamicCast(OSNumber,provider->getProperty(kIOHIDVendorIDKey));
_productID = OSDynamicCast(OSNumber,provider->getProperty(kIOHIDProductIDKey));
_locationID = OSDynamicCast(OSNumber,provider->getProperty(kIOHIDLocationIDKey));
setProperty(kIOHIDTransportKey, _transport);
setProperty(kIOHIDVendorIDKey, _vendorID);
setProperty(kIOHIDProductIDKey, _productID);
setProperty(kIOHIDLocationIDKey, _locationID);
setProperty(kIOHIDCountryCodeKey, provider->getProperty(kIOHIDCountryCodeKey));
productIDVal = _productID ? _productID->unsigned16BitValue() : 0;
vendorIDVal = _vendorID ? _vendorID->unsigned16BitValue() : 0;
if (!super::start(provider))
return false;
if ( ((productIDVal == kprodUSBAndyISOKbd) || (productIDVal == kprodUSBCosmoISOKbd) ||
(productIDVal == kprodQ6ISOKbd) || (productIDVal == kprodQ30ISOKbd))
&& (vendorIDVal == kIOUSBVendorIDAppleComputer))
{
_usb_2_adb_keymap[0x35] = 0x0a; _usb_2_adb_keymap[0x64] = 0x32;
}
xml_swap_CTRL_CAPSLOCK = OSDynamicCast( OSNumber, provider->getProperty("Swap control and capslock"));
if (xml_swap_CTRL_CAPSLOCK)
{
if ( xml_swap_CTRL_CAPSLOCK->unsigned32BitValue())
{
char temp;
temp = _usb_2_adb_keymap[0x39]; _usb_2_adb_keymap[0x39] = _usb_2_adb_keymap[0xe0]; _usb_2_adb_keymap[0xe0] = temp;
}
}
xml_swap_CMD_ALT = OSDynamicCast( OSNumber, provider->getProperty("Swap command and alt"));
if (xml_swap_CMD_ALT)
{
if ( xml_swap_CMD_ALT->unsigned32BitValue())
{
char temp;
temp = _usb_2_adb_keymap[0xe2]; _usb_2_adb_keymap[0xe2] = _usb_2_adb_keymap[0xe3]; _usb_2_adb_keymap[0xe3] = temp;
temp = _usb_2_adb_keymap[0xe6]; _usb_2_adb_keymap[0xe6] = _usb_2_adb_keymap[0xe7]; _usb_2_adb_keymap[0xe7] = temp;
}
}
_asyncLEDThread = thread_call_allocate((thread_call_func_t)_asyncLED, (thread_call_param_t)this);
if ( _fKeyValuePtr )
{
OSDictionary * matchingDictionary;
matchingDictionary = IOService::serviceMatching( "IOHIDConsumer" );
if( matchingDictionary )
{
matchingDictionary->setObject(kIOHIDTransportKey, _transport);
matchingDictionary->setObject(kIOHIDVendorIDKey, _vendorID);
matchingDictionary->setObject(kIOHIDProductIDKey, _productID);
matchingDictionary->setObject(kIOHIDLocationIDKey, _locationID);
_publishNotify = addNotification( gIOPublishNotification,
matchingDictionary,
&IOHIDKeyboard::_publishNotificationHandler,
this, 0 );
}
findSecondaryKeys();
setProperty(kIOHIDFKeyModeKey, _fKeyMode, sizeof(_fKeyMode));
}
return true;
}
bool IOHIDKeyboard::_publishNotificationHandler(
void * target,
void * ,
IOService * newService )
{
IOHIDKeyboard * self = (IOHIDKeyboard *) target;
IORecursiveLockLock(self->_keyboardLock);
if( OSDynamicCast(IOHIDConsumer,newService) &&
(self->_consumer != newService) )
{
if( self->_consumer) {
if (self->_consumer->isDispatcher()) {
self->_consumer->stop(self);
self->_consumer->detach(self);
}
self->_consumer->release();
}
self->_consumer = newService;
self->_consumer->retain();
if ( self->_publishNotify )
{
self->_publishNotify->remove();
self->_publishNotify = 0;
}
}
IORecursiveLockUnlock(self->_keyboardLock);
return true;
}
void IOHIDKeyboard::stop(IOService * provider)
{
if (_asyncLEDThread)
{
thread_call_cancel(_asyncLEDThread);
thread_call_free(_asyncLEDThread);
_asyncLEDThread = 0;
}
IORecursiveLockLock(_keyboardLock);
if( _consumer) {
if (_consumer->isDispatcher()) {
_consumer->stop(this);
_consumer->detach(this);
}
_consumer->release();
_consumer = 0;
}
IORecursiveLockUnlock(_keyboardLock);
super::stop(provider);
}
void IOHIDKeyboard::free()
{
if (_oldArraySelectors)
{
IOFree(_oldArraySelectors, sizeof(UInt32) * _keyCodeArrayValuePtrArray->getCount());
_oldArraySelectors = 0;
}
if (_keyCodeArrayValuePtrArray)
{
_keyCodeArrayValuePtrArray->release();
_keyCodeArrayValuePtrArray = 0;
}
if (_publishNotify)
{
_publishNotify->remove();
_publishNotify = 0;
}
if (_keyboardLock)
{
IORecursiveLockLock(_keyboardLock);
IORecursiveLock* tempLock = _keyboardLock;
_keyboardLock = NULL;
IORecursiveLockUnlock(tempLock);
IORecursiveLockFree(tempLock);
}
super::free();
}
bool
IOHIDKeyboard::determineKeyboard(IOHIDDevice *owner)
{
OSDictionary * pair;
OSArray * usagePairs;
OSNumber * usagePage;
OSNumber * usage;
UInt32 usageVal, usagePageVal;
bool isKeyboard = false;
usagePairs = OSDynamicCast(OSArray, owner->getProperty(kIOHIDDeviceUsagePairsKey));
for (int i=0; usagePairs && i<usagePairs->getCount(); i++)
{
if (!(pair = usagePairs->getObject(i)))
continue;
usagePage = pair->getObject(kIOHIDDeviceUsagePageKey);
usage = pair->getObject(kIOHIDDeviceUsageKey);
usagePageVal = (usagePage) ? usagePage->unsigned32BitValue() : 0;
usageVal = (usage) ? usage->unsigned32BitValue() : 0;
if ( (usagePageVal == kHIDPage_GenericDesktop) &&
((usageVal == kHIDUsage_GD_Keyboard) || (usageVal == kHIDUsage_GD_Keypad)) )
{
isKeyboard = true;
break;
}
}
return isKeyboard;
}
bool
IOHIDKeyboard::findDesiredElements(OSArray *elements, IOHIDDevice *owner)
{
OSNumber * fnUsage;
OSNumber * fnUsagePage;
IOHIDElement * element;
UInt32 usage, usagePage;
UInt32 count;
if (!determineKeyboard(owner))
return false;
if (!elements)
return false;
if (!(_keyCodeArrayValuePtrArray = OSArray::withCapacity(6)))
return false;
fnUsage = OSDynamicCast(OSNumber, owner->getProperty(kFnModifierUsageKey));
fnUsagePage = OSDynamicCast(OSNumber,owner->getProperty(kFnModifierUsagePageKey));
count = elements->getCount();
for (int i=0; i<count; i++)
{
element = elements->getObject(i);
usagePage = element->getUsagePage();
usage = element->getUsage();
if (!_fKeyValuePtr && fnUsage && fnUsagePage &&
(usage == fnUsage->unsigned32BitValue()) &&
(usagePage == fnUsagePage->unsigned32BitValue()))
{
_fKeyValuePtr = element->getElementValue()->value;
}
switch (usagePage)
{
case kHIDPage_KeyboardOrKeypad:
if ((usage >= kHIDUsage_KeyboardLeftControl) &&
(usage <= kHIDUsage_KeyboardRightGUI) &&
(_modifierValuePtrs[usage - kHIDUsage_KeyboardLeftControl] == 0))
{
_modifierValuePtrs[usage - kHIDUsage_KeyboardLeftControl] =
element->getElementValue()->value;
}
else if ((usage == 0xffffffff) && (element->getReportCount() == 1))
{
_keyCodeArrayValuePtrArray->setObject(element);
}
break;
case kHIDPage_LEDs:
if (((usage == kHIDUsage_LED_NumLock) ||
(usage == kHIDUsage_LED_CapsLock)) &&
(_ledValuePtrs[usage - kHIDUsage_LED_NumLock] == 0))
{
_ledValuePtrs[usage - kHIDUsage_LED_NumLock] = element->getElementValue()->value;
_ledCookies[usage - kHIDUsage_LED_NumLock] = element->getElementCookie();
_numLeds++;
}
break;
default:
break;
}
}
UInt32 keyCount = _keyCodeArrayValuePtrArray->getCount();
if (keyCount)
{
_oldArraySelectors = (UInt32 *)IOMalloc(sizeof(UInt32) * keyCount);
if ( !_oldArraySelectors )
return false;
bzero(_oldArraySelectors, sizeof(UInt32) * keyCount);
}
return (keyCount);
}
void IOHIDKeyboard::findSecondaryKeys()
{
OSString * mappingString;
char * str;
int i, index, count;
mappingString = OSDynamicCast(OSString,_provider->getProperty(kNumPadUsageMapKey));
if (mappingString)
{
count = mappingString->getLength();
str = mappingString->getCStringNoCopy();
for (i=0; i<count; i+=10)
{
index = strtol(&(str[i]), NULL, 16);
_secondaryKeys[index].bits |= kSecondaryKeyNumPad;
_secondaryKeys[index].numPadUsage = strtol(&(str[i+5]), NULL, 16);
}
}
mappingString = OSDynamicCast(OSString,_provider->getProperty(kFnSpecialKeyMapKey));
if (mappingString)
{
count = mappingString->getLength();
str = mappingString->getCStringNoCopy();
for (i=0; i<count; i+=10)
{
index = strtol(&(str[i]), NULL, 16);
_secondaryKeys[index].bits |= kSecondaryKeyFnSpecial;
_secondaryKeys[index].specialKey = strtol(&(str[i+5]), NULL, 16);
}
}
mappingString = OSDynamicCast(OSString,_provider->getProperty(kFnNonSpecialUsageMapKey));
if (mappingString)
{
count = mappingString->getLength();
str = mappingString->getCStringNoCopy();
for (i=0; i<count; i+=10)
{
index = strtol(&(str[i]), NULL, 16);
_secondaryKeys[index].bits |= kSecondaryKeyFnNonSpecial;
_secondaryKeys[index].fnUsage = strtol(&(str[i+5]), NULL, 16);
}
}
}
void
IOHIDKeyboard::handleReport()
{
UInt8 modifier=0;
UInt32 alpha = 0;
bool found;
AbsoluteTime now;
UInt8 seq_key, i; IOHIDElement * element;
found = true;
for (seq_key = 0; seq_key < _keyCodeArrayValuePtrArray->getCount(); seq_key++) {
if ((element = _keyCodeArrayValuePtrArray->getObject(seq_key)) &&
(element->getElementValue()->value[0] != 1))
found = false;
}
if (found) return;
clock_get_uptime(&now);
for (i = 0; i < 8; i++)
{
modifier |= _modifierValuePtrs[i][0] << i;
}
if (modifier == _oldmodifier)
{
}
else {
if ((modifier & kUSB_LEFT_CONTROL_BIT) && !(_oldmodifier & kUSB_LEFT_CONTROL_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe0], true, now); }
else if ((_oldmodifier & kUSB_LEFT_CONTROL_BIT) && !(modifier & kUSB_LEFT_CONTROL_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe0], false, now);
}
if ((modifier & kUSB_RIGHT_CONTROL_BIT) && !(_oldmodifier & kUSB_RIGHT_CONTROL_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe4], true, now); }
else if ((_oldmodifier & kUSB_RIGHT_CONTROL_BIT) && !(modifier & kUSB_RIGHT_CONTROL_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe4], false, now);
}
if ((modifier & kUSB_LEFT_SHIFT_BIT) && !(_oldmodifier & kUSB_LEFT_SHIFT_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe1], true, now);
}
else if ((_oldmodifier & kUSB_LEFT_SHIFT_BIT) && !(modifier & kUSB_LEFT_SHIFT_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe1], false, now);
}
if ((modifier & kUSB_RIGHT_SHIFT_BIT) && !(_oldmodifier & kUSB_RIGHT_SHIFT_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe5], true, now);
}
else if ((_oldmodifier & kUSB_RIGHT_SHIFT_BIT) && !(modifier & kUSB_RIGHT_SHIFT_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe5], false, now);
}
if ((modifier & kUSB_LEFT_ALT_BIT) && !(_oldmodifier & kUSB_LEFT_ALT_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe2], true, now);
}
else if ((_oldmodifier & kUSB_LEFT_ALT_BIT) && !(modifier & kUSB_LEFT_ALT_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe2], false, now);
}
if ((modifier & kUSB_RIGHT_ALT_BIT) && !(_oldmodifier & kUSB_RIGHT_ALT_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe6], true, now);
}
else if ((_oldmodifier & kUSB_RIGHT_ALT_BIT) && !(modifier & kUSB_RIGHT_ALT_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe6], false, now);
}
if ((modifier & kUSB_LEFT_FLOWER_BIT) && !(_oldmodifier & kUSB_LEFT_FLOWER_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe3], true, now);
}
else if ((_oldmodifier & kUSB_LEFT_FLOWER_BIT) && !(modifier & kUSB_LEFT_FLOWER_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe3], false, now);
}
if ((modifier & kUSB_RIGHT_FLOWER_BIT) && !(_oldmodifier & kUSB_RIGHT_FLOWER_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe7], true, now);
}
else if ((_oldmodifier & kUSB_RIGHT_FLOWER_BIT) && !(modifier & kUSB_RIGHT_FLOWER_BIT))
{
dispatchKeyboardEvent(_usb_2_adb_keymap[0xe7], false, now);
}
}
if ( _fKeyValuePtr && ( *_fKeyValuePtr != _lastFKeyValue ) )
{
_lastFKeyValue = *_fKeyValuePtr;
dispatchKeyboardEvent(0x3f, _lastFKeyValue, now);
}
for (seq_key = 0; seq_key < _keyCodeArrayValuePtrArray->getCount(); seq_key++)
{
alpha = _oldArraySelectors[seq_key];
if (alpha == 0) {
continue;
}
found = false;
for (i = 0; i < _keyCodeArrayValuePtrArray->getCount(); i++) {
if ((element = _keyCodeArrayValuePtrArray->getObject(i)) &&
(element->getElementValue()->value[0] == alpha))
{
found = true; break; }
}
if (!found)
{
if (!filterSecondaryFnSpecialKey(&alpha, false, now))
if (!filterSecondaryFnNonSpecialKey(&alpha, false, now))
if (!filterSecondaryNumPadKey(&alpha, false, now))
dispatchKeyboardEvent(_usb_2_adb_keymap[alpha], false, now);
}
}
for (seq_key = 0; seq_key < _keyCodeArrayValuePtrArray->getCount(); seq_key++)
{
if (!(element = _keyCodeArrayValuePtrArray->getObject(seq_key)))
continue;
alpha = element->getElementValue()->value[0];
if (alpha == 0) {
continue;
}
found = false;
for (i = 0; i < _keyCodeArrayValuePtrArray->getCount(); i++)
{
if (alpha == _oldArraySelectors[i])
{
found = true;
break;
}
}
if (!found)
{
if (!filterSecondaryFnSpecialKey(&alpha, true, now))
if (!filterSecondaryFnNonSpecialKey(&alpha, true, now))
if (!filterSecondaryNumPadKey(&alpha, true, now))
dispatchKeyboardEvent(_usb_2_adb_keymap[alpha], true, now); }
}
_oldmodifier = modifier;
for (i = 0; i < _keyCodeArrayValuePtrArray->getCount(); i++)
{
if (!(element = _keyCodeArrayValuePtrArray->getObject(i)))
continue;
_oldArraySelectors[i] = element->getElementValue()->value[0];
}
}
#define SHOULD_SWAP_FN_SPECIAL_KEY(key, down) \
((_secondaryKeys[key].bits & kSecondaryKeyFnSpecial) && \
(!( _lastFKeyValue ^ _fKeyMode ) || (!down && \
(_secondaryKeys[key].swapping & kSecondaryKeyFnSpecial))))
#define SHOULD_SWAP_FN_NUM_PAD_KEY(key, down) \
((_secondaryKeys[key].bits & kSecondaryKeyFnNonSpecial) && \
(( _lastFKeyValue ^ \
(_fKeyMode && _stickyKeysOn) ) || (!down && \
(_secondaryKeys[key].swapping & kSecondaryKeyFnNonSpecial))))
#define SHOULD_SWAP_NUM_PAD_KEY(key, down) \
((numLock() || ( !down && \
(_secondaryKeys[key].swapping & kSecondaryKeyNumPad))))
bool IOHIDKeyboard::filterSecondaryFnSpecialKey(int * usage, bool down, AbsoluteTime ts)
{
if ( !_fKeyValuePtr )
return false;
if (SHOULD_SWAP_FN_SPECIAL_KEY(*usage, down))
{
if (down)
_secondaryKeys[*usage].swapping |= kSecondaryKeyFnSpecial;
else
_secondaryKeys[*usage].swapping = 0;
IORecursiveLockLock(_keyboardLock);
if (!_consumer)
{
_consumer = IOHIDConsumer::Dispatcher(this);
if (_consumer &&
(!_consumer->attach(this) ||
!_consumer->start(this)))
{
_consumer->release();
_consumer = 0;
}
}
if (_consumer)
{
_consumer->dispatchSpecialKeyEvent(
_secondaryKeys[*usage].specialKey, down, ts);
}
IORecursiveLockUnlock(_keyboardLock);
return true;
}
return false;
}
bool IOHIDKeyboard::filterSecondaryFnNonSpecialKey(int * usage, bool down, AbsoluteTime ts)
{
if ( !_fKeyValuePtr )
return false;
if (SHOULD_SWAP_FN_NUM_PAD_KEY(*usage, down))
{
if (down)
_secondaryKeys[*usage].swapping |= kSecondaryKeyFnNonSpecial;
else
_secondaryKeys[*usage].swapping = 0;
*usage = _secondaryKeys[*usage].fnUsage;
}
return false;
}
bool IOHIDKeyboard::filterSecondaryNumPadKey(int * usage, bool down, AbsoluteTime ts)
{
if ( !_fKeyValuePtr )
return false;
if (SHOULD_SWAP_NUM_PAD_KEY(*usage, down))
{
if (_secondaryKeys[*usage].bits & kSecondaryKeyNumPad)
{
if (down)
_secondaryKeys[*usage].swapping |= kSecondaryKeyNumPad;
else
_secondaryKeys[*usage].swapping = 0;
*usage = _secondaryKeys[*usage].numPadUsage;
}
else if ( down )
return true;
}
return false;
}
void
IOHIDKeyboard::_asyncLED(OSObject *target)
{
IOHIDKeyboard *me = OSDynamicCast(IOHIDKeyboard, target);
me->Set_LED_States( me->_ledState );
}
void
IOHIDKeyboard::Set_LED_States(UInt8 ledState)
{
IOHIDElementCookie cookies[_numLeds];
int cookieCount = 0;
for (int i=0; i<2; i++)
{
if (_ledValuePtrs[i])
{
_ledValuePtrs[i][0] = (ledState >> i) & 1;
cookies[cookieCount++] = _ledCookies[i];
}
}
_provider->postElementValues(cookies, cookieCount);
}
void
IOHIDKeyboard::setAlphaLockFeedback ( bool LED_state)
{
UInt8 newState = _ledState;
if (LED_state) newState |= kUSB_CAPSLOCKLED_SET; else
newState &= ~kUSB_CAPSLOCKLED_SET;
if (newState != _ledState)
{
_ledState = newState;
if (_asyncLEDThread)
thread_call_enter(_asyncLEDThread);
}
}
void
IOHIDKeyboard::setNumLockFeedback ( bool LED_state)
{
UInt8 newState = _ledState;
if (LED_state)
newState |= kUSB_NUMLOCKLED_SET; else
newState &= ~kUSB_NUMLOCKLED_SET;
if (newState != _ledState)
{
_ledState = newState;
if (_asyncLEDThread)
thread_call_enter(_asyncLEDThread);
}
}
unsigned
IOHIDKeyboard::getLEDStatus (void )
{
unsigned ledState = 0;
for (int i=0; i<2; i++)
{
if (_ledValuePtrs[i])
{
ledState |= _ledValuePtrs[i][0] << i;
}
}
}
UInt32
IOHIDKeyboard::maxKeyCodes (void )
{
return 0x80;
}
UInt32
IOHIDKeyboard::deviceType ( void )
{
UInt32 id;
OSNumber *xml_handlerID;
xml_handlerID = OSDynamicCast( OSNumber, _provider->getProperty("alt_handler_id"));
if (xml_handlerID)
{
id = xml_handlerID->unsigned32BitValue();
}
else
{
id = handlerID();
}
return id;
}
UInt32
IOHIDKeyboard::interfaceID ( void )
{
return NX_EVS_DEVICE_INTERFACE_ADB; }
UInt32
IOHIDKeyboard::handlerID ( void )
{
UInt32 ret_id = 2; UInt16 productIDVal = _productID ? _productID->unsigned16BitValue() : 0;
UInt16 vendorIDVal = _vendorID ? _vendorID->unsigned16BitValue() : 0;
if (vendorIDVal == 0x045e) {
if (productIDVal == 0x000b) ret_id = 2; }
if (vendorIDVal == kIOUSBVendorIDAppleComputer)
switch (productIDVal)
{
case kprodUSBCosmoANSIKbd: ret_id = kgestUSBCosmoANSIKbd; break;
case kprodUSBCosmoISOKbd: ret_id = kgestUSBCosmoISOKbd; break;
case kprodUSBCosmoJISKbd: ret_id = kgestUSBCosmoJISKbd; break;
case kprodUSBAndyANSIKbd: ret_id = kgestUSBAndyANSIKbd; break;
case kprodUSBAndyISOKbd: ret_id = kgestUSBAndyISOKbd; break;
case kprodUSBAndyJISKbd: ret_id = kgestUSBAndyJISKbd; break;
case kprodQ6ANSIKbd: ret_id = kgestQ6ANSIKbd;
break;
case kprodQ6ISOKbd: ret_id = kgestQ6ISOKbd;
break;
case kprodQ6JISKbd: ret_id = kgestQ6JISKbd;
break;
case kprodQ30ANSIKbd: ret_id = kgestQ30ANSIKbd;
break;
case kprodQ30ISOKbd: ret_id = kgestQ30ISOKbd;
break;
case kprodQ30JISKbd: ret_id = kgestQ30JISKbd;
break;
case kprodFountainANSIKbd: ret_id = kgestFountainANSIKbd;
break;
case kprodFountainISOKbd: ret_id = kgestFountainISOKbd;
break;
case kprodFountainJISKbd: ret_id = kgestFountainJISKbd;
break;
case kprodSantaANSIKbd: ret_id = kgestSantaANSIKbd;
break;
case kprodSantaISOKbd: ret_id = kgestSantaISOKbd;
break;
case kprodSantaJISKbd: ret_id = kgestSantaJISKbd;
break;
default: ret_id = kgestUSBCosmoANSIKbd;
break;
}
return ret_id; }
const unsigned char *
IOHIDKeyboard::defaultKeymapOfLength (UInt32 * length )
{
if ( _fKeyValuePtr )
{
static const unsigned char appleUSAFKeyMap[] = {
0x00,0x00,
0x0b, 0x01,0x01,0x38,
0x02,0x01,0x3b,
0x03,0x01,0x3a,
0x04,0x01,0x37,
0x05,0x10,0x52,0x41,0x53,0x54,0x55,0x45,0x58,0x57,0x56,0x5b,0x5c,
0x43,0x4b,0x51,0x4e,0x59,
0x06,0x01,0x72,
0x07,0x01,0x3f, 0x09,0x01,0x3c, 0x0a,0x01,0x3e, 0x0b,0x01,0x3d, 0x0c,0x01,0x36,
0x7f,0x0d,0x00,0x61,
0x00,0x41,0x00,0x01,0x00,0x01,0x00,0xca,0x00,0xc7,0x00,0x01,0x00,0x01,0x0d,0x00,
0x73,0x00,0x53,0x00,0x13,0x00,0x13,0x00,0xfb,0x00,0xa7,0x00,0x13,0x00,0x13,0x0d,
0x00,0x64,0x00,0x44,0x00,0x04,0x00,0x04,0x01,0x44,0x01,0xb6,0x00,0x04,0x00,0x04,
0x0d,0x00,0x66,0x00,0x46,0x00,0x06,0x00,0x06,0x00,0xa6,0x01,0xac,0x00,0x06,0x00,
0x06,0x0d,0x00,0x68,0x00,0x48,0x00,0x08,0x00,0x08,0x00,0xe3,0x00,0xeb,0x00,0x00,
0x18,0x00,0x0d,0x00,0x67,0x00,0x47,0x00,0x07,0x00,0x07,0x00,0xf1,0x00,0xe1,0x00,
0x07,0x00,0x07,0x0d,0x00,0x7a,0x00,0x5a,0x00,0x1a,0x00,0x1a,0x00,0xcf,0x01,0x57,
0x00,0x1a,0x00,0x1a,0x0d,0x00,0x78,0x00,0x58,0x00,0x18,0x00,0x18,0x01,0xb4,0x01,
0xce,0x00,0x18,0x00,0x18,0x0d,0x00,0x63,0x00,0x43,0x00,0x03,0x00,0x03,0x01,0xe3,
0x01,0xd3,0x00,0x03,0x00,0x03,0x0d,0x00,0x76,0x00,0x56,0x00,0x16,0x00,0x16,0x01,
0xd6,0x01,0xe0,0x00,0x16,0x00,0x16,0x02,0x00,0x3c,0x00,0x3e,0x0d,0x00,0x62,0x00,
0x42,0x00,0x02,0x00,0x02,0x01,0xe5,0x01,0xf2,0x00,0x02,0x00,0x02,0x0d,0x00,0x71,
0x00,0x51,0x00,0x11,0x00,0x11,0x00,0xfa,0x00,0xea,0x00,0x11,0x00,0x11,0x0d,0x00,
0x77,0x00,0x57,0x00,0x17,0x00,0x17,0x01,0xc8,0x01,0xc7,0x00,0x17,0x00,0x17,0x0d,
0x00,0x65,0x00,0x45,0x00,0x05,0x00,0x05,0x00,0xc2,0x00,0xc5,0x00,0x05,0x00,0x05,
0x0d,0x00,0x72,0x00,0x52,0x00,0x12,0x00,0x12,0x01,0xe2,0x01,0xd2,0x00,0x12,0x00,
0x12,0x0d,0x00,0x79,0x00,0x59,0x00,0x19,0x00,0x19,0x00,0xa5,0x01,0xdb,0x00,0x19,
0x00,0x19,0x0d,0x00,0x74,0x00,0x54,0x00,0x14,0x00,0x14,0x01,0xe4,0x01,0xd4,0x00,
0x14,0x00,0x14,0x0a,0x00,0x31,0x00,0x21,0x01,0xad,0x00,0xa1,0x0e,0x00,0x32,0x00,
0x40,0x00,0x32,0x00,0x00,0x00,0xb2,0x00,0xb3,0x00,0x00,0x00,0x00,0x0a,0x00,0x33,
0x00,0x23,0x00,0xa3,0x01,0xba,0x0a,0x00,0x34,0x00,0x24,0x00,0xa2,0x00,0xa8,0x0e,
0x00,0x36,0x00,0x5e,0x00,0x36,0x00,0x1e,0x00,0xb6,0x00,0xc3,0x00,0x1e,0x00,0x1e,
0x0a,0x00,0x35,0x00,0x25,0x01,0xa5,0x00,0xbd,0x0a,0x00,0x3d,0x00,0x2b,0x01,0xb9,
0x01,0xb1,0x0a,0x00,0x39,0x00,0x28,0x00,0xac,0x00,0xab,0x0a,0x00,0x37,0x00,0x26,
0x01,0xb0,0x01,0xab,0x0e,0x00,0x2d,0x00,0x5f,0x00,0x1f,0x00,0x1f,0x00,0xb1,0x00,
0xd0,0x00,0x1f,0x00,0x1f,0x0a,0x00,0x38,0x00,0x2a,0x00,0xb7,0x00,0xb4,0x0a,0x00,
0x30,0x00,0x29,0x00,0xad,0x00,0xbb,0x0e,0x00,0x5d,0x00,0x7d,0x00,0x1d,0x00,0x1d,
0x00,0x27,0x00,0xba,0x00,0x1d,0x00,0x1d,0x0d,0x00,0x6f,0x00,0x4f,0x00,0x0f,0x00,
0x0f,0x00,0xf9,0x00,0xe9,0x00,0x0f,0x00,0x0f,0x0d,0x00,0x75,0x00,0x55,0x00,0x15,
0x00,0x15,0x00,0xc8,0x00,0xcd,0x00,0x15,0x00,0x15,0x0e,0x00,0x5b,0x00,0x7b,0x00,
0x1b,0x00,0x1b,0x00,0x60,0x00,0xaa,0x00,0x1b,0x00,0x1b,0x0d,0x00,0x69,0x00,0x49,
0x00,0x09,0x00,0x09,0x00,0xc1,0x00,0xf5,0x00,0x09,0x00,0x09,0x0d,0x00,0x70,0x00,
0x50,0x00,0x10,0x00,0x10,0x01,0x70,0x01,0x50,0x00,0x10,0x00,0x10,0x10,0x00,0x0d,
0x00,0x03,0x0d,0x00,0x6c,0x00,0x4c,0x00,0x0c,0x00,0x0c,0x00,0xf8,0x00,0xe8,0x00,
0x0c,0x00,0x0c,0x0d,0x00,0x6a,0x00,0x4a,0x00,0x0a,0x00,0x0a,0x00,0xc6,0x00,0xae,
0x00,0x0a,0x00,0x0a,0x0a,0x00,0x27,0x00,0x22,0x00,0xa9,0x01,0xae,0x0d,0x00,0x6b,
0x00,0x4b,0x00,0x0b,0x00,0x0b,0x00,0xce,0x00,0xaf,0x00,0x0b,0x00,0x0b,0x0a,0x00,
0x3b,0x00,0x3a,0x01,0xb2,0x01,0xa2,0x0e,0x00,0x5c,0x00,0x7c,0x00,0x1c,0x00,0x1c,
0x00,0xe3,0x00,0xeb,0x00,0x1c,0x00,0x1c,0x0a,0x00,0x2c,0x00,0x3c,0x00,0xcb,0x01,
0xa3,0x0a,0x00,0x2f,0x00,0x3f,0x01,0xb8,0x00,0xbf,0x0d,0x00,0x6e,0x00,0x4e,0x00,
0x0e,0x00,0x0e,0x00,0xc4,0x01,0xaf,0x00,0x0e,0x00,0x0e,0x0d,0x00,0x6d,0x00,0x4d,
0x00,0x0d,0x00,0x0d,0x01,0x6d,0x01,0xd8,0x00,0x0d,0x00,0x0d,0x0a,0x00,0x2e,0x00,
0x3e,0x00,0xbc,0x01,0xb3,0x02,0x00,0x09,0x00,0x19,0x0c,0x00,0x20,0x00,0x00,0x00,
0x80,0x00,0x00,0x0a,0x00,0x60,0x00,0x7e,0x00,0x60,0x01,0xbb,0x02,0x00,0x7f,0x00,
0x08,0xff,0x02,0x00,0x1b,0x00,0x7e,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,
0xff,0xff,0x00,0x00,0x2e,0xff,0x00,0x00,
0x2a,0xff,0x00,0x00,0x2b,0xff,0x00,0x00,0x1b,0xff,0xff,0xff,0x0e,0x00,0x2f,0x00,
0x5c,0x00,0x2f,0x00,0x1c,0x00,0x2f,0x00,0x5c,0x00,0x00,0x0a,0x00,0x00,0x00,0x0d, 0xff,0x00,0x00,0x2d,0xff,0xff,0x0e,0x00,0x3d,0x00,0x7c,0x00,0x3d,0x00,0x1c,0x00,
0x3d,0x00,0x7c,0x00,0x00,0x18,0x46,0x00,0x00,0x30,0x00,0x00,0x31,0x00,0x00,0x32,
0x00,0x00,0x33,0x00,0x00,0x34,0x00,0x00,0x35,0x00,0x00,0x36,0x00,0x00,0x37,0xff,
0x00,0x00,0x38,0x00,0x00,0x39,0xff,0xff,0xff,0x00,0xfe,0x24,0x00,0xfe,0x25,0x00,
0xfe,0x26,0x00,0xfe,0x22,0x00,0xfe,0x27,0x00,0xfe,0x28,0xff,0x00,0xfe,0x2a,0xff,
0x00,0xfe,0x32,0x00,0xfe,0x35,0x00,0xfe,0x33,0xff,0x00,0xfe,0x29,0xff,0x00,0xfe,0x2b,0xff,
0x00,0xfe,0x34,0xff,0x00,0xfe,0x2e,0x00,0xfe,0x30,0x00,0xfe,0x2d,0x00,0xfe,0x23,
0x00,0xfe,0x2f,0x00,0xfe,0x21,0x00,0xfe,0x31,0x00,0xfe,0x20,
0x00,0x01,0xac, 0x00,0x01,0xae, 0x00,0x01,0xaf, 0x00,0x01,0xad, 0x0f,0x02,0xff,0x04,
0x00,0x31,0x02,0xff,0x04,0x00,0x32,0x02,0xff,0x04,0x00,0x33,0x02,0xff,0x04,0x00,
0x34,0x02,0xff,0x04,0x00,0x35,0x02,0xff,0x04,0x00,0x36,0x02,0xff,0x04,0x00,0x37,
0x02,0xff,0x04,0x00,0x38,0x02,0xff,0x04,0x00,0x39,0x02,0xff,0x04,0x00,0x30,0x02,
0xff,0x04,0x00,0x2d,0x02,0xff,0x04,0x00,0x3d,0x02,0xff,0x04,0x00,0x70,0x02,0xff,
0x04,0x00,0x5d,0x02,0xff,0x04,0x00,0x5b,
0x07, 0x04,0x39, 0x05,0x72, 0x06,0x7f, 0x07,0x4a, 0x00,0x48, 0x01,0x49, 0x0a,0x47 };
*length = sizeof(appleUSAFKeyMap);
return appleUSAFKeyMap;
}
static const unsigned char appleUSAKeyMap[] = {
0x00,0x00,
0x0a, 0x01,0x01,0x38,
0x02,0x01,0x3b,
0x03,0x01,0x3a,
0x04,0x01,0x37,
0x05,0x11,0x52,0x41,0x4c,0x53,0x54,0x55,0x45,0x58,0x57,0x56,0x5b,0x5c,
0x43,0x4b,0x51,0x4e,0x59,
0x06,0x01,0x72,
0x09,0x01,0x3c, 0x0a,0x01,0x3e, 0x0b,0x01,0x3d, 0x0c,0x01,0x36,
0x7f,0x0d,0x00,0x61,
0x00,0x41,0x00,0x01,0x00,0x01,0x00,0xca,0x00,0xc7,0x00,0x01,0x00,0x01,0x0d,0x00,
0x73,0x00,0x53,0x00,0x13,0x00,0x13,0x00,0xfb,0x00,0xa7,0x00,0x13,0x00,0x13,0x0d,
0x00,0x64,0x00,0x44,0x00,0x04,0x00,0x04,0x01,0x44,0x01,0xb6,0x00,0x04,0x00,0x04,
0x0d,0x00,0x66,0x00,0x46,0x00,0x06,0x00,0x06,0x00,0xa6,0x01,0xac,0x00,0x06,0x00,
0x06,0x0d,0x00,0x68,0x00,0x48,0x00,0x08,0x00,0x08,0x00,0xe3,0x00,0xeb,0x00,0x00,
0x18,0x00,0x0d,0x00,0x67,0x00,0x47,0x00,0x07,0x00,0x07,0x00,0xf1,0x00,0xe1,0x00,
0x07,0x00,0x07,0x0d,0x00,0x7a,0x00,0x5a,0x00,0x1a,0x00,0x1a,0x00,0xcf,0x01,0x57,
0x00,0x1a,0x00,0x1a,0x0d,0x00,0x78,0x00,0x58,0x00,0x18,0x00,0x18,0x01,0xb4,0x01,
0xce,0x00,0x18,0x00,0x18,0x0d,0x00,0x63,0x00,0x43,0x00,0x03,0x00,0x03,0x01,0xe3,
0x01,0xd3,0x00,0x03,0x00,0x03,0x0d,0x00,0x76,0x00,0x56,0x00,0x16,0x00,0x16,0x01,
0xd6,0x01,0xe0,0x00,0x16,0x00,0x16,0x02,0x00,0x3c,0x00,0x3e,0x0d,0x00,0x62,0x00,
0x42,0x00,0x02,0x00,0x02,0x01,0xe5,0x01,0xf2,0x00,0x02,0x00,0x02,0x0d,0x00,0x71,
0x00,0x51,0x00,0x11,0x00,0x11,0x00,0xfa,0x00,0xea,0x00,0x11,0x00,0x11,0x0d,0x00,
0x77,0x00,0x57,0x00,0x17,0x00,0x17,0x01,0xc8,0x01,0xc7,0x00,0x17,0x00,0x17,0x0d,
0x00,0x65,0x00,0x45,0x00,0x05,0x00,0x05,0x00,0xc2,0x00,0xc5,0x00,0x05,0x00,0x05,
0x0d,0x00,0x72,0x00,0x52,0x00,0x12,0x00,0x12,0x01,0xe2,0x01,0xd2,0x00,0x12,0x00,
0x12,0x0d,0x00,0x79,0x00,0x59,0x00,0x19,0x00,0x19,0x00,0xa5,0x01,0xdb,0x00,0x19,
0x00,0x19,0x0d,0x00,0x74,0x00,0x54,0x00,0x14,0x00,0x14,0x01,0xe4,0x01,0xd4,0x00,
0x14,0x00,0x14,0x0a,0x00,0x31,0x00,0x21,0x01,0xad,0x00,0xa1,0x0e,0x00,0x32,0x00,
0x40,0x00,0x32,0x00,0x00,0x00,0xb2,0x00,0xb3,0x00,0x00,0x00,0x00,0x0a,0x00,0x33,
0x00,0x23,0x00,0xa3,0x01,0xba,0x0a,0x00,0x34,0x00,0x24,0x00,0xa2,0x00,0xa8,0x0e,
0x00,0x36,0x00,0x5e,0x00,0x36,0x00,0x1e,0x00,0xb6,0x00,0xc3,0x00,0x1e,0x00,0x1e,
0x0a,0x00,0x35,0x00,0x25,0x01,0xa5,0x00,0xbd,0x0a,0x00,0x3d,0x00,0x2b,0x01,0xb9,
0x01,0xb1,0x0a,0x00,0x39,0x00,0x28,0x00,0xac,0x00,0xab,0x0a,0x00,0x37,0x00,0x26,
0x01,0xb0,0x01,0xab,0x0e,0x00,0x2d,0x00,0x5f,0x00,0x1f,0x00,0x1f,0x00,0xb1,0x00,
0xd0,0x00,0x1f,0x00,0x1f,0x0a,0x00,0x38,0x00,0x2a,0x00,0xb7,0x00,0xb4,0x0a,0x00,
0x30,0x00,0x29,0x00,0xad,0x00,0xbb,0x0e,0x00,0x5d,0x00,0x7d,0x00,0x1d,0x00,0x1d,
0x00,0x27,0x00,0xba,0x00,0x1d,0x00,0x1d,0x0d,0x00,0x6f,0x00,0x4f,0x00,0x0f,0x00,
0x0f,0x00,0xf9,0x00,0xe9,0x00,0x0f,0x00,0x0f,0x0d,0x00,0x75,0x00,0x55,0x00,0x15,
0x00,0x15,0x00,0xc8,0x00,0xcd,0x00,0x15,0x00,0x15,0x0e,0x00,0x5b,0x00,0x7b,0x00,
0x1b,0x00,0x1b,0x00,0x60,0x00,0xaa,0x00,0x1b,0x00,0x1b,0x0d,0x00,0x69,0x00,0x49,
0x00,0x09,0x00,0x09,0x00,0xc1,0x00,0xf5,0x00,0x09,0x00,0x09,0x0d,0x00,0x70,0x00,
0x50,0x00,0x10,0x00,0x10,0x01,0x70,0x01,0x50,0x00,0x10,0x00,0x10,0x10,0x00,0x0d,
0x00,0x03,0x0d,0x00,0x6c,0x00,0x4c,0x00,0x0c,0x00,0x0c,0x00,0xf8,0x00,0xe8,0x00,
0x0c,0x00,0x0c,0x0d,0x00,0x6a,0x00,0x4a,0x00,0x0a,0x00,0x0a,0x00,0xc6,0x00,0xae,
0x00,0x0a,0x00,0x0a,0x0a,0x00,0x27,0x00,0x22,0x00,0xa9,0x01,0xae,0x0d,0x00,0x6b,
0x00,0x4b,0x00,0x0b,0x00,0x0b,0x00,0xce,0x00,0xaf,0x00,0x0b,0x00,0x0b,0x0a,0x00,
0x3b,0x00,0x3a,0x01,0xb2,0x01,0xa2,0x0e,0x00,0x5c,0x00,0x7c,0x00,0x1c,0x00,0x1c,
0x00,0xe3,0x00,0xeb,0x00,0x1c,0x00,0x1c,0x0a,0x00,0x2c,0x00,0x3c,0x00,0xcb,0x01,
0xa3,0x0a,0x00,0x2f,0x00,0x3f,0x01,0xb8,0x00,0xbf,0x0d,0x00,0x6e,0x00,0x4e,0x00,
0x0e,0x00,0x0e,0x00,0xc4,0x01,0xaf,0x00,0x0e,0x00,0x0e,0x0d,0x00,0x6d,0x00,0x4d,
0x00,0x0d,0x00,0x0d,0x01,0x6d,0x01,0xd8,0x00,0x0d,0x00,0x0d,0x0a,0x00,0x2e,0x00,
0x3e,0x00,0xbc,0x01,0xb3,0x02,0x00,0x09,0x00,0x19,0x0c,0x00,0x20,0x00,0x00,0x00,
0x80,0x00,0x00,0x0a,0x00,0x60,0x00,0x7e,0x00,0x60,0x01,0xbb,0x02,0x00,0x7f,0x00,
0x08,0xff,0x02,0x00,0x1b,0x00,0x7e,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,
0xff,0xff,0x00,0x00,0x2e,0xff,0x00,0x00,
0x2a,0xff,0x00,0x00,0x2b,0xff,0x00,0x00,0x1b,0xff,0xff,0xff,0x0e,0x00,0x2f,0x00,
0x5c,0x00,0x2f,0x00,0x1c,0x00,0x2f,0x00,0x5c,0x00,0x00,0x0a,0x00,0x00,0x00,0x0d, 0xff,0x00,0x00,0x2d,0xff,0xff,0x0e,0x00,0x3d,0x00,0x7c,0x00,0x3d,0x00,0x1c,0x00,
0x3d,0x00,0x7c,0x00,0x00,0x18,0x46,0x00,0x00,0x30,0x00,0x00,0x31,0x00,0x00,0x32,
0x00,0x00,0x33,0x00,0x00,0x34,0x00,0x00,0x35,0x00,0x00,0x36,0x00,0x00,0x37,0xff,
0x00,0x00,0x38,0x00,0x00,0x39,0xff,0xff,0xff,0x00,0xfe,0x24,0x00,0xfe,0x25,0x00,
0xfe,0x26,0x00,0xfe,0x22,0x00,0xfe,0x27,0x00,0xfe,0x28,0xff,0x00,0xfe,0x2a,0xff,
0x00,0xfe,0x32,0x00,0xfe,0x35,0x00,0xfe,0x33,0xff,0x00,0xfe,0x29,0xff,0x00,0xfe,0x2b,0xff,
0x00,0xfe,0x34,0xff,0x00,0xfe,0x2e,0x00,0xfe,0x30,0x00,0xfe,0x2d,0x00,0xfe,0x23,
0x00,0xfe,0x2f,0x00,0xfe,0x21,0x00,0xfe,0x31,0x00,0xfe,0x20,
0x00,0x01,0xac, 0x00,0x01,0xae, 0x00,0x01,0xaf, 0x00,0x01,0xad, 0x0f,0x02,0xff,0x04,
0x00,0x31,0x02,0xff,0x04,0x00,0x32,0x02,0xff,0x04,0x00,0x33,0x02,0xff,0x04,0x00,
0x34,0x02,0xff,0x04,0x00,0x35,0x02,0xff,0x04,0x00,0x36,0x02,0xff,0x04,0x00,0x37,
0x02,0xff,0x04,0x00,0x38,0x02,0xff,0x04,0x00,0x39,0x02,0xff,0x04,0x00,0x30,0x02,
0xff,0x04,0x00,0x2d,0x02,0xff,0x04,0x00,0x3d,0x02,0xff,0x04,0x00,0x70,0x02,0xff,
0x04,0x00,0x5d,0x02,0xff,0x04,0x00,0x5b,
0x07, 0x04,0x39, 0x05,0x72, 0x06,0x7f, 0x07,0x4a, 0x00,0x48, 0x01,0x49, 0x0a,0x47 };
*length = sizeof(appleUSAKeyMap);
return appleUSAKeyMap;
}
IOReturn IOHIDKeyboard::setParamProperties( OSDictionary * dict )
{
OSNumber *datan;
if (_keyboardLock)
IORecursiveLockLock (_keyboardLock);
if ( _fKeyValuePtr )
{
if (datan = OSDynamicCast(OSNumber, dict->getObject(kIOHIDFKeyModeKey)))
{
_fKeyMode = datan->unsigned8BitValue();
setProperty(kIOHIDFKeyModeKey, datan);
}
}
if (datan = OSDynamicCast(OSNumber, dict->getObject(kIOHIDStickyKeysOnKey)))
{
_stickyKeysOn = datan->unsigned8BitValue();
}
if (_keyboardLock)
IORecursiveLockUnlock (_keyboardLock);
return super::setParamProperties(dict);
}
static bool CompareProperty( IOService * owner, OSDictionary * matching, const char * key )
{
OSObject * value;
bool matches;
value = matching->getObject( key );
if( value)
matches = value->isEqualTo( owner->getProperty( key ));
else
matches = true;
return matches;
}
bool IOHIDKeyboard::matchPropertyTable(OSDictionary * table, SInt32 * score)
{
bool match = true;
if (super::matchPropertyTable(table, score) == false) return false;
if (!CompareProperty(this, table, kIOHIDLocationIDKey) ||
!CompareProperty(this, table, kIOHIDTransportKey) ||
!CompareProperty(this, table, kIOHIDVendorIDKey) ||
!CompareProperty(this, table, kIOHIDProductIDKey))
match = false;
return match;
}