1.檢視input子系統支援哪些裝置:cat /proc/bus/input/devices
2.應用程式如何使用:
fd_mouse=open("dev/input/event0",o_rdwr); //event1表示滑鼠事件,
input下的裝置檔案主裝置號都為13,如下圖所示:
根據開啟裝置的主裝置號為13,知道為input輸入子系統,根據裝置的次裝置號,可以知道其對應的handler 。
一.handler註冊
1.handler 以evdev.c為例
static const struct file_operations evdev_fops = ;
static struct input_handler evdev_handler = ;
static int __init evdev_init(void)
2.input
void input_register_handler(struct input_handler *handler)
static int input_open_file(struct inode *inode, struct file *file)
其中的input_table為handler中的,即將handler的fop賦給file->f_op;以後當應用程式呼叫read函式時,即呼叫handler下的evdev_reaad函式。
二.device註冊
1.device 以gpio_keys.c為例
struct input_dev *input;
input = input_allocate_device();
input->evbit[0] = bit(ev_key);
input->evbit[0] = bit(ev_key);
input->name = pdev->name;
input->phys = "gpio-keys/input0";
input->dev.parent = &pdev->dev;
input->id.bustype = bus_host;
input->id.vendor = 0x0001;
input->id.product = 0x0001;
input->id.version = 0x0100;
error = input_register_device(input);
2.input
int input_register_device(struct input_dev *dev)
三.handler與device相關聯
在input_register_hadler與input_register_device中,有handler與device註冊時,先將其鏈結到全域性handler/dev鍊錶,然後遍歷全域性dev/handler鍊錶,查詢是否有相匹配的,然後呼叫input_attach_handler(dev, handler)函式
static int input_attach_handler(struct input_dev *dev, struct input_handler *handler)
static int evdev_connect(struct input_handler *handler, struct input_dev *dev,const struct input_device_id *id)
int input_register_handle(struct input_handle *handle)
evdev的id_table支援的裝置為
.id_table = evdev_ids,
static const struct input_device_id evdev_ids = , /* matches all devices */ 表示支援所有的輸入裝置
, /* terminating zero entry */
};
對比下keyboard.c的id_table所支援的裝置
.id_table = kbd_ids,
static const struct input_device_id kbd_ids = , //支援按鍵裝置
},, },
, /* terminating entry */
};
以gpio_keys.c為例
input->evbit[0] = bit(ev_key);
從此可以看出,該device裝置為按鍵裝置,上面兩個handler都支援該裝置。
三,資料讀
當應用程式呼叫read函式時,跳轉到evdev_read函式
static ssize_t evdev_read(struct file *file, char __user *buffer, size_t count, loff_t *ppos)
wait在何處wake_up了?通過查詢得知,在evdev_event中
static void evdev_event(struct input_handle *handle, unsigned int type, unsigned int code, int value)
那麼evdev_event在何處呼叫?
evdev_event與input_event相關聯,即input_event何時被呼叫?
在gpio_keys.c中可以檢視到
static irqreturn_t gpio_keys_isr(int irq, void *dev_id)
input.c中
void input_event(struct input_dev *dev, unsigned int type, unsigned int code, int value)
break;
}list_for_each_entry(handle, &dev->h_list, d_node)
if (handle->open) //如果open函式被呼叫過handle->handler->event(handle, type, code, value); //呼叫handler的event函式即evdev_event函式
}
input輸入子系統分析1
input register handler struct input handler handler 1 在開始的時候讓input handler的h list指向自己,也就是乙個空的迴圈鍊錶,在後來註冊input handle的時候 讓input handle的hnode與匹配的input ha...
Linux輸入子系統分析一
輸入裝置分散不堪,用input子系統可以對分散的,不同類別的輸入裝置進行統一驅動。好處 1.統一了物理形態各異的輸入裝置相似的裝置處理,例如各種滑鼠,鍵盤,觸控螢幕。2.提供了用於分發輸入報告給使用者應用程式的簡單事件介面。你的驅動不必建立管理 dev節點以及相關的訪問方法。因此他能夠很方便的呼叫輸...
Linux 輸入子系統分析(二)
linux 輸入子系統分析 一 linux 輸入子系統分析 二 分析乙個核心提供的input handler input dev驅動程式的工作主要是 申請一些硬體資源,如註冊中斷等,申請input dev並設定,然後呼叫核心層提供的input register device函式進行註冊。裝置有資料時...