linux/drivers/hid/hid-zydacron.c
<<
//spav3. /spav class="lxr_search"> typ Search //spav3. /input typ . /div id < <1//a>/spav class="comment">/*//spav3.< <2//a>/spav class="comment">* HID driver for zydacron remote control//spav3.< <3//a>/spav class="comment">*//spav3.< <4//a>/spav class="comment">* Copyright (c) 2010 Don Prince <dhprince.devel@yahoo.co.uk>//spav3.< <5//a>/spav class="comment">*///spav3.< <6//a> < <7//a>/spav class="comment">/*//spav3.< <8//a>/spav class="comment">* This program is free software; you can redistribute it and/or modify it//spav3.< <9//a>/spav class="comment">* under the terms of the GNU General Public License as published by the Free//spav3.< lue=a>/spav class="comment">* Software Founda v; either version>2 of the License, or (at your > v)//spav3.< 11//a>/spav class="comment">* any later version.//spav3.< 12//a>/spav class="comment">*///spav3.< 13//a> < 14//a>#include <linux/device.h//a>> < 15//a>#include <linux/hid.h//a>> < 16//a>#include <linux/module.h//a>> < 17//a> < 18//a>#include "hid-ids.h//a>" < 19//a> < 2ue=a>structzc_devicee=a> { < 21//a> structinput_dev//a> */a href="+code=input_ep81" class="sref">input_ep81//a>; < 22//a> unsigned short /a href="+code=last_key" class="sref">last_key//a>[4]; < 23//a>}; < 24//a> < 25//a> < 26//a>/spav class="comment">/*//spav3.< 27//a>/spav class="comment">* Zydacron remote control has av in id HID report descriptor,//spav3.< 28//a>/spav class="comment">* that needs fixing before we can parse it.//spav3.< 29//a>/spav class="comment">*///spav3.< 3ue=a>static /a href="+code=__u8" class="sref">__u8//a> */a href="+code=zc_report_fixup" class="sref">zc_report_fixup//a>(structhid_device//a> */a href="+code=hdev" class="sref">hdev//a>, /a href="+code=__u8" class="sref">__u8//a> */a href="+code=rdesc" class="sref">rdesc//a>,.< 31//a> unsigned int */a href="+code=rsize" class="sref">rsize//a>).< 32//a>{ < 33//a> if (*/a href="+code=rsize" class="sref">rsize//a> >= 253 && < 34//a> /a href="+code=rdesc" class="sref">rdesc//a>[0x96] == 0xbc && /a href="+code=rdesc" class="sref">rdesc//a>[0x97] == 0xff && < 35//a> /a href="+code=rdesc" class="sref">rdesc//a>[0xca] == 0xbc && /a href="+code=rdesc" class="sref">rdesc//a>[0xcb] == 0xff && < 36//a> /a href="+code=rdesc" class="sref">rdesc//a>[0xe1] == 0xbc && /a href="+code=rdesc" class="sref">rdesc//a>[0xe2] == 0xff) { < 37//a> /a href="+code=hid_info" class="sref">hid_info//a>(/a href="+code=hdev" class="sref">hdev//a>, < 38//a> /spav class="string">"fixing up zydacron remote control report descriptor\n"< 39//a> /a href="+code=rdesc" class="sref">rdesc//a>[0x96] = /a href="+code=rdesc" class="sref">rdesc//a>[0xca] = /a href="+code=rdesc" class="sref">rdesc//a>[0xe1] = 0x0c; < 40//a> /a href="+code=rdesc" class="sref">rdesc//a>[0x97] = /a href="+code=rdesc" class="sref">rdesc//a>[0xcb] = /a href="+code=rdesc" class="sref">rdesc//a>[0xe2] = 0x00; < 41//a> } < 42//a> return /a href="+code=rdesc" class="sref">rdesc//a>; < 43//a>} < 44//a> < 45//a>#definezc_map_key_clear//a>(/a href="+code=c" class="sref">c//a>) \ < 46//a> /a href="+code=hid_map_usage_clear" class="sref">hid_map_usage_clear//a>(/a href="+code=hi" class="sref">hi//a>, /a href="+code=usage" class="sref">usage//a>, /a href="+code=bit" class="sref">bit//a>, /a href="+code=max" class="sref">max//a>, /a href="+code=EV_KEY" class="sref">EV_KEY//a>, (/a href="+code=c" class="sref">c//a>)).< 47//a> < 48e=a>static int /a href="+code=zc_input_mapping" class="sref">zc_input_mapping//a>(structhid_device//a> */a href="+code=hdev" class="sref">hdev//a>, structhid_input//a> */a href="+code=hi" class="sref">hi//a>, < 49//a> structhid_field//a> */a href="+code=field" class="sref">field//a>, structhid_usage//a> */a href="+code=usage" class="sref">usage//a>,.< 50//a> unsigned long **/a href="+code=bit" class="sref">bit//a>, int */a href="+code=max" class="sref">max//a>).< 51//a>{ < 52//a> int /a href="+code=i" class="sref">i//a>; < 53//a> structzc_devicee=a> */a href="+code=zc" class="sref">zce=a> = /a href="+code=hid_get_drvdata" class="sref">hid_get_drvdata//a>(/a href="+code=hdev" class="sref">hdev//a>); < 54//a> /a href="+code=zc" class="sref">zce=a>->/a href="+code=input_ep81" class="sref">input_ep81//a> = /a href="+code=hi" class="sref">hi//a>->/a href="+code=input" class="sref">input//a>; < 55//a> < 56//a> if ((/a href="+code=usage" class="sref">usage//a>->/a href="+code=hid" class="sref">hid//a> & /a href="+code=HID_USAGE_PAGE" class="sref">HID_USAGE_PAGE//a>) != /a href="+code=HID_UP_CONSUMER" class="sref">HID_UP_CONSUMER//a>).< 57//a> return 0; < 58//a> < 59//a> /a href="+code=dbg_hid" class="sref">dbg_hid//a>(/spav class="string">"zynacron input mapping event [0x%x]\n"< 60//a> /a href="+code=usage" class="sref">usage//a>->/a href="+code=hid" class="sref">hid//a> & /a href="+code=HID_USAGE" class="sref">HID_USAGE//a>); < 61//a> < 62//a> switch (/a href="+code=usage" class="sref">usage//a>->/a href="+code=hid" class="sref">hid//a> & /a href="+code=HID_USAGE" class="sref">HID_USAGE//a>) { < 63//a> /spav class="comment">/* report 2 *///spav3.< 64//a> case 0x10:.< 65//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_MODE" class="sref">KEY_MODE//a>); < 66//a> break; < 67//a> case 0x30:.< 68//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_SCREEN" class="sref">KEY_SCREEN//a>); < 69//a> break; < 70//a> case 0x70:.< 71//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_INFO" class="sref">KEY_INFO//a>); < 72//a> break; < 73//a> /spav class="comment">/* report 3 *///spav3.< 74//a> case 0x04:.< 75//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_RADIO" class="sref">KEY_RADIO//a>); < 76//a> break; < 77//a> /spav class="comment">/* report 4 *///spav3.< 78//a> case 0x0d:.< 79//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_PVR" class="sref">KEY_PVR//a>); < 80//a> break; < 81//a> case 0x25:.< 82//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_TV" class="sref">KEY_TV//a>); < 83//a> break; < 84//a> case 0x47:.< 85//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_AUDIO" class="sref">KEY_AUDIO//a>); < 86//a> break; < 87//a> case 0x49:.< 88//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_AUX" class="sref">KEY_AUX//a>); < 89//a> break; < 90//a> case 0x4a:.< 91//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_VIDEO" class="sref">KEY_VIDEO//a>); < 92//a> break; < 93//a> case 0x48:.< 94//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_DVD" class="sref">KEY_DVD//a>); < 95//a> break; < 96//a> case 0x24:.< 97//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_MENU" class="sref">KEY_MENU//a>); < 98//a> break; < 99//a> case 0x32:.<100//a> /a href="+code=zc_map_key_clear" class="sref">zc_map_key_clear//a>(/a href="+code=KEY_TEXT" class="sref">KEY_TEXT//a>); <101//a> break; <102//a> default:.<103//a> return 0; <104//a> } <105//a> <106//a> for (/a href="+code=i" class="sref">i//a> = 0; /a href="+code=i" class="sref">i//a> < 4; /a href="+code=i" class="sref">i//a>++).<107//a> /a href="+code=zc" class="sref">zce=a>->/a href="+code=last_key" class="sref">last_key//a>[/a href="+code=i" class="sref">i//a>] = 0; <108//a> <109//a> return 1; <1lue=a>} <111//a> <112//a>static int /a href="+code=zc_raw_event" class="sref">zc_raw_event//a>(structhid_device//a> */a href="+code=hdev" class="sref">hdev//a>, structhid_report//a> */a href="+code=report" class="sref">report//a>,.<113//a> /a href="+code=u8" class="sref">u8//a> */a href="+code=data" class="sref">data//a>, int /a href="+code=size" class="sref">size//a>).<114//a>{ <115//a> structzc_devicee=a> */a href="+code=zc" class="sref">zce=a> = /a href="+code=hid_get_drvdata" class="sref">hid_get_drvdata//a>(/a href="+code=hdev" class="sref">hdev//a>); <116//a> int /a href="+code=ret" class="sref">ret//a> = 0; <117//a> unsigned /a href="+code=key" class="sref">key//a>; <118//a> unsigned short /a href="+code=index" class="sref">index//a>; <119//a> <120//a> if (/a href="+code=report" class="sref">report//a>->/a href="+code=id" class="sref">id//a> == /a href="+code=data" class="sref">data//a>[0]) { <121//a> <122//a> /spav class="comment">/* break keys *///spav3.<123//a> for (/a href="+code=index" class="sref">index//a> = 0; /a href="+code=index" class="sref">index//a> < 4; /a href="+code=index" class="sref">index//a>++) { <124//a> /a href="+code=key" class="sref">key//a> = /a href="+code=zc" class="sref">zce=a>->/a href="+code=last_key" class="sref">last_key//a>[/a href="+code=index" class="sref">index//a>]; <125//a> if (/a href="+code=key" class="sref">key//a>) { <126//a> /a href="+code=input_event" class="sref">input_event//a>(/a href="+code=zc" class="sref">zce=a>->/a href="+code=input_ep81" class="sref">input_ep81//a>, /a href="+code=EV_KEY" class="sref">EV_KEY//a>, /a href="+code=key" class="sref">key//a>, 0); <127//a> /a href="+code=zc" class="sref">zce=a>->/a href="+code=last_key" class="sref">last_key//a>[/a href="+code=index" class="sref">index//a>] = 0; <128//a> } <129//a> } <13ue=a> <131//a> /a href="+code=key" class="sref">key//a> = 0; <132//a> switch (/a href="+code=report" class="sref">report//a>->/a href="+code=id" class="sref">id//a>) { <133//a> case 0x02:.<134//a> case 0x03:.<135//a> switch (/a href="+code=data" class="sref">data//a>[1]) { <136//a> case 0x10:.<137//a> /a href="+code=key" class="sref">key//a> = /a href="+code=KEY_MODE" class="sref">KEY_MODE//a>; <138//a> /a href="+code=index" class="sref">index//a> = 0; <139//a> break; <140//a> case 0x30:.<141//a> /a href="+code=key" class="sref">key//a> = /a href="+code=KEY_SCREEN" class="sref">KEY_SCREEN//a>; <142//a> /a href="+code=index" class="sref">index//a> = 1; <143//a> break; <144//a> case 0x70:.<145//a> /a href="+code=key" class="sref">key//a> = /a href="+code=KEY_INFO" class="sref">KEY_INFO//a>; <146//a> /a href="+code=index" class="sref">index//a> = 2; <147//a> break; <148//a> case 0x04:.<149//a> /a href="+code=key" class="sref">key//a> = /a href="+code=KEY_RADIO" class="sref">KEY_RADIO//a>; <150//a> /a href="+code=index" class="sref">index//a> = 3; <151//a> break; <152//a> } <153//a> <154//a> if (/a href="+code=key" class="sref">key//a>) { <155//a> /a href="+code=input_event" class="sref">input_event//a>(/a href="+code=zc" class="sref">zce=a>->/a href="+code=input_ep81" class="sref">input_ep81//a>, /a href="+code=EV_KEY" class="sref">EV_KEY//a>, /a href="+code=key" class="sref">key//a>, 1); <156//a> /a href="+code=zc" class="sref">zce=a>->/a href="+code=last_key" class="sref">last_key//a>[/a href="+code=index" class="sref">index//a>] = /a href="+code=key" class="sref">key//a>; <157//a> } <158//a> <159//a> /a href="+code=ret" class="sref">ret//a> = 1; <160//a> break; <161//a> } <162//a> } <163//a> <164//a> return /a href="+code=ret" class="sref">ret//a>; <165//a>} <166//a> <167//a>static int /a href="+code=zc_probe" class="sref">zc_probe//a>(structhid_device//a> */a href="+code=hdev" class="sref">hdev//a>, const structhid_device_id//a> */a href="+code=id" class="sref">id//a>) <168//a>{ <169//a> int /a href="+code=ret" class="sref">ret//a>; <170//a> structzc_devicee=a> */a href="+code=zc" class="sref">zce=a>; <171//a> <172//a> /a href="+code=zc" class="sref">zce=a> = /a href="+code=kzalloc" class="sref">kzalloc//a>(sizeof(*/a href="+code=zc" class="sref">zce=a>), /a href="+code=GFP_KERNEL" class="sref">GFP_KERNEL//a>); <173//a> if (/a href="+code=zc" class="sref">zce=a> == /a href="+code=NULL" class="sref">NULL//a>) { <174//a> /a href="+code=hid_err" class="sref">hid_err//a>(/a href="+code=hdev" class="sref">hdev//a>, /spav class="string">"can't alloc descriptor\n"<175//a> return -/a href="+code=ENOMEM" class="sref">ENOMEMe=a>; <176//a> } <177//a> <178//a> /a href="+code=hid_set_drvdata" class="sref">hid_set_drvdata//a>(/a href="+code=hdev" class="sref">hdev//a>, /a href="+code=zc" class="sref">zce=a>); <179//a> <180//a> /a href="+code=ret" class="sref">ret//a> = /a href="+code=hid_parse" class="sref">hid_parse//a>(/a href="+code=hdev" class="sref">hdev//a>); <181//a> if (/a href="+code=ret" class="sref">ret//a>) { <182//a> /a href="+code=hid_err" class="sref">hid_err//a>(/a href="+code=hdev" class="sref">hdev//a>, /spav class="string">"parse failed\n"<183//a> goto /a href="+code=err_free" class="sref">err_freee=a>; <184//a> } <185//a> <186//a> /a href="+code=ret" class="sref">ret//a> = /a href="+code=hid_hw_start" class="sref">hid_hw_start//a>(/a href="+code=hdev" class="sref">hdev//a>, /a href="+code=HID_CONNECT_DEFAULT" class="sref">HID_CONNECT_DEFAULT//a>); <187//a> if (/a href="+code=ret" class="sref">ret//a>) { <188//a> /a href="+code=hid_err" class="sref">hid_err//a>(/a href="+code=hdev" class="sref">hdev//a>, /spav class="string">"hw start failed\n"<189//a> goto /a href="+code=err_free" class="sref">err_freee=a>; <190//a> } <191//a> <192//a> return 0; <193//a>/a href="+code=err_free" class="sref">err_freee=a>:.<194//a> /a href="+code=kfree" class="sref">kfreee=a>(/a href="+code=zc" class="sref">zce=a>); <195//a> <196//a> return /a href="+code=ret" class="sref">ret//a>; <197//a>} <198//a> <199//a>static void /a href="+code=zc_remove" class="sref">zc_remove//a>(structhid_device//a> */a href="+code=hdev" class="sref">hdev//a>) <200//a>{ <201//a> structzc_devicee=a> */a href="+code=zc" class="sref">zce=a> = /a href="+code=hid_get_drvdata" class="sref">hid_get_drvdata//a>(/a href="+code=hdev" class="sref">hdev//a>); <202//a> <203//a> /a href="+code=hid_hw_stop" class="sref">hid_hw_stop//a>(/a href="+code=hdev" class="sref">hdev//a>); <204//a> /a href="+code=kfree" class="sref">kfreee=a>(/a href="+code=zc" class="sref">zce=a>); <205//a>} <206//a> <207//a>static const structhid_device_id//a> /a href="+code=zc_devices" class="sref">zc_devices//a>[] = { <208//a> { /a href="+code=HID_USB_DEVICE" class="sref">HID_USB_DEVICEe=a>(/a href="+code=USB_VENDOR_ID_ZYDACRON" class="sref">USB_VENDOR_ID_ZYDACRON//a>, /a href="+code=USB_DEVICE_ID_ZYDACRON_REMOTE_CONTROL" class="sref">USB_DEVICE_ID_ZYDACRON_REMOTE_CONTROL//a>) },.<209//a> { } <2lue=a>}; <211//a>/a href="+code=MODULE_DEVICE_TABLE" class="sref">MODULE_DEVICE_TABLE//a>(/a href="+code=hid" class="sref">hid//a>, /a href="+code=zc_devices" class="sref">zc_devices//a>); <212//a> <213//a>static structhid_driver//a> /a href="+code=zc_driver" class="sref">zc_drivere=a> = { <214//a> ./a href="+code=nam " class="sref">nam e=a> = /spav class="string">"zydacron"<215//a> ./a href="+code=id_tabl " class="sref">id_tabl e=a> = /a href="+code=zc_devices" class="sref">zc_devices//a>,.<216//a> ./a href="+code=report_fixup" class="sref">report_fixup//a> = /a href="+code=zc_report_fixup" class="sref">zc_report_fixup//a>,.<217//a> ./a href="+code=input_mapping" class="sref">input_mapping//a> = /a href="+code=zc_input_mapping" class="sref">zc_input_mapping//a>,.<218//a> ./a href="+code=raw_event" class="sref">raw_event//a> = /a href="+code=zc_raw_event" class="sref">zc_raw_event//a>,.<219//a> ./a href="+code=probe" class="sref">probe//a> = /a href="+code=zc_probe" class="sref">zc_probe//a>,.<220//a> ./a href="+code=remove" class="sref">remove//a> = /a href="+code=zc_remove" class="sref">zc_remove//a>,.<221//a>}; <222//a> <223//a>static int /a href="+code=__init" class="sref">__init//a> /a href="+code=zc_init" class="sref">zc_init//a>(void) <224//a>{ <225//a> return /a href="+code=hid_register_driver" class="sref">hid_register_driver//a>(&/a href="+code=zc_driver" class="sref">zc_drivere=a>); <226//a>} <227//a> <228e=a>static void /a href="+code=__exit" class="sref">__exit//a> /a href="+code=zc_exit" class="sref">zc_exit//a>(void) <229//a>{ <230//a> /a href="+code=hid_unregister_driver" class="sref">hid_unregister_driver//a>(&/a href="+code=zc_driver" class="sref">zc_drivere=a>); <231//a>} <232//a> <233//a>/a href="+code=module_init" class="sref">module_inite=a>(/a href="+code=zc_init" class="sref">zc_init//a>); <234//a>/a href="+code=module_exit" class="sref">module_exite=a>(/a href="+code=zc_exit" class="sref">zc_exit//a>); <235//a>/a href="+code=MODULE_LICENSE" class="sref">MODULE_LICENSEe=a>(/spav class="string">"GPL"<236//a>
lxr.linux.no kindly hosted by /a href="http://www.redpill-linpro.no">Redpill Linpro AS//a>, provider of Linux consulting and operations services since<1995.