不同的輸入裝置 (如按鍵、鍵盤、觸控螢幕、滑鼠等) 都有它們的差異性 (如中斷、讀鍵值/座標值是裝置相關的) 及共同性 (如輸入事件的緩衝區管理以及字元裝置驅動的file_operations介面則對輸入裝置是通用的) ,因此在linux核心中設計了input輸入子系統來完成輸入裝置之間的共性工作,而我們只需要使用輸入子系統提供的工具 (也就是函式) 來完成這些「差異」就行了input輸入子系統由核心層(input.c)、輸入裝置驅動程式 (差異)、輸入事件驅動程式 (共性) 三部分組成
輸入裝置註冊函式:
int
input_register_device
(struct input_dev *dev)
裝置處理註冊函式
int
input_register_handler
(struct input_handler *handler)
匹配函式:
static
intinput_attach_handler
(struct input_dev *dev,
struct input_handler *handler)
匹配過程:
當註冊裝置或者處理程式時,會呼叫input_attach_handler()
函式檢測input_dev.id
與input_handler.id_table
是否匹配,如果匹配則呼叫input_handler.connect
函式進行連線。
對於驅動裝置的分析,可以從載入函式入手
static
int __init input_init
(void
)
其中,input_fops
結構體如下:
static
const
struct file_operations input_fops =
;
input_open_file()
函式:
static
intinput_open_file
(struct inode *inode,
struct file *file)
結合輸入子系統框架部分可知,驅動處理部分呼叫input_register_handler()
函式向input.c
註冊處理函式,會將裝置的處理函式handler
填入input_table
陣列中。開啟input系統時,在input_open_file()
中會通過次裝置號在input_table
陣列中找到對應的handler
,並用handler->fops
替換掉file->f_op
,達到開啟對應輸入裝置的驅動的目的
以evdev為例:
static
intevdev_connect
(struct input_handler *handler,
struct input_dev *dev,
const
struct input_device_id *id)
其中,input_register_handle()
函式如下:
int
input_register_handle
(struct input_handle *handle)
由此可見建立連線步驟:
分配乙個input_handle
結構體
填充結構體,使
input_handle.dev = input_dev;
// 指向左邊的input_dev
input_handle.handler = input_handler;
// 指向右邊的input_handler
註冊:input_handler->h_list =
&input_handle;
inpu_dev->h_list =
&input_handle;
建立連線後,對於裝置,可通過h_list
找到input_handle
,再通過input_handle.handler
找到對應驅動;對於驅動,可通過h_list
找到input_handle
,再通過input_handle.dev
找到對應的裝置。
以evdev為例:
evdev_read()
函式如下:
static ssize_t evdev_read
(struct file *file,
char __user * buffer, size_t count, loff_t *ppos)
通過搜尋evdev->wait
知當evdev_read()
休眠時,會由evdev_event()
函式喚醒
static
void
evdev_event
(struct input_handle *handle,
unsigned
int type,
unsigned
int code,
int value)
分析猜測,evdev_event()
應該在input_dev
那層被呼叫
以核心中gpio_key.c為例
static irqreturn_t gpio_keys_isr
(int irq,
void
*dev_id)
其中,上報函式input_event()
函式如下:
void
input_event
(struct input_dev *dev,
unsigned
int type,
unsigned
int code,
int value)
即建立連線後,裝置層通過上報事件的方式向驅動層報告硬體裝置的動作,喚醒驅動層,讓其完成相應處理。 Linux裝置驅動之 input子系統
什麼是input input子系統處理輸入事務,任何輸入裝置的驅動程式都可以通過input輸入子系統提供的介面註冊到核心,利用子系統提供的功能來與使用者空間互動。輸入裝置一般包括鍵盤,滑鼠,觸控螢幕等,在核心中都是以輸入裝置出現的。下面分析input輸入子系統的結構,以及功能實現。linux中inp...
Linux裝置驅動開發 input子系統
基於linux 2.6.22.6核心,arm9 s3c2440開發板 原始碼分析 drivers input input.c input init err register chrdev input major,input input fops static const struct file op...
input 輸入裝置平台驅動
1,主機環境 vmare下linux5.7 384記憶體。2,編譯編譯環境 arm linux gcc v4.4.3 3,開發板 fl2440,4m nor flash,256m nand flash。移植參照mini2440的示例 1 首先是平台裝置的註冊 include include incl...