Linux Input Subsystem Principle Understanding (original)

Source: Internet
Author: User

Linux Input Subsystem principle Understanding (original)

Previously learned the individual key device driver as well as the mouse drive, in fact, in Linux to implement these device drivers, there is a more recommended method, is input subsystem. Usually our keys, touch-screen, mouse and other input devices can be used to simplify the driver and device driver.

Input subsystem principle

The architecture of the Linux input subsystem can be divided into three levels, namely: drive layer, input core layer, event processing layer, three somewhat similar to PHP's MVC pattern, meaning that each level is only responsible for a single function, no need to participate in other functions, a bit similar to the package of functions, well, nonsense not much to say, Three levels of specific functions are as follows:

(1) Drive layer: Convert the underlying hardware input into a unified event type, reporting 0 to the input core, and simply, the driver is responsible for reporting things.

(2) Input core layer: To provide the input device registration and operation interface for the drive layer.

For example: 1. Register the device with the Input_register_device function;

2. Notify the event processing layer to handle the event;

3. Generate the appropriate device information under/proc.

(3) Event processing layer: The main function is to interact with the user space. Contains the FoPs interface that provides the driver, generates the corresponding device file node nod and other functions under/dev.

In general, summarize a large section of the above:

An event, such as mouse movement, the keyboard presses the event, first through the
The drive layer driver--the input core layer inputcore--> Event processing layer Events handler--> The order of user space userspace to complete the response of the event.

Device description

The input device is described by the INPUT_DEV structure.

In the input subsystem to implement the device driver, the core of the drive is to report to the System button, touch screen, mouse and other events, do not care about the file interface, because these interfaces are event processing layer handler to achieve.

Well, the principle is almost the same, next talk about the implementation of the drive

Drive implementation

1. Event Support

First a device driver, we should tell the input subsystem what events it supports and which keys, for example, through the Set_bit () function:

Set_bit (Ev_key,button_dev.evbit); Tells the input subsystem when to support keystrokes

There are two members in a Struct Input_dev:

Evbit: Event Type

Keybit: Key Type

Event Type:

Ev_rst Reset Ev_key button

Ev_rel relative coordinates ev_abs absolute coordinates

Ev_msc Other Ev_lec LEDs

EV_SND Sound Ev_rep Repeat

EV_FF Force Feedback

However, when the event type is Ev_key, you also need to indicate the key type:

Btn_left: Left mouse button btn_0: number 0 key

Btn_right: Right mouse button btn_1: Number 1 key

Btn_middle: Middle mouse button

2. Reporting Events

When the event really happens, our drive layer should report the Ev_key,ev_rel,ev_abs and other events to input core, the report functions are:

Void input_report_key (struct input_dev *dev,unsigned int code, int value)

Void Input_report_rel (struct input_dev *dev,unsigned int code, int value)

Void input_report_abs (struct input_dev *dev,unsigned int code, int value)

Code: If the event type is Ev_key, then the code is the keyboard code for the device, such as the keyboard key code value is 0~127, the mouse key code value is 0x110 ~ 0x116 specific refer to the Include/linux/input.h file

Value: The values of the event. If the event type is Ev_key, press the key to the value of 1 and release is 0

3. End of report

Input_sync () is used to tell input core: the report has ended

For example, in a touchscreen device driver, the entire reporting event process for a single click is as follows:

Input_report_abs (Input_dev, abs_x, X); Report X coordinate

Input_report_abs (Input_dev, abs_y, Y); Report y-coordinate

Input_report_abs (Input_dev, abs_pressure, 1); The report event type is pressed and value value is 1

Input_sync (Input_dev); Report Complete, synchronization event

A local function of a key driver:

Report an event in a key interrupt

Static void Buton_interrupt (int irq, void *dummy, struct pt_regs *fp)

{

Note that all the keys here are reported, whether it's a No. 0 or 1th button

Input_report_key (&button_dev, Btn_0, INB (button_port0));

Input_report_key (&button_dev, btn_1, INB (Button_port1));

Input_sync (&button_dev); Report Complete, synchronization event

At this point, the input core layer and the event processing layer will form the corresponding data for the collected event type and put it into file operation and buffer to read from the user space

}

Driver initialization function

Static int __init button_init (void) {

Request interrupted because the Keystroke event report is executed in the interrupt

If (REQUEST_IRQ (button_irq,button_interrupt, 0, "button", NULL))

Return–ebusy;

Set_bit (Ev_key, button_dev.evbit); Tells the input subsystem to support Ev_key events
Set_bit (Btn_0, button_dev.keybit); Tells the input subsystem to support the NO. 0 number key
Set_bit (btn_1, button_dev.keybit); Tells the input subsystem to support the 1th number key

Input_register_device (&button_dev); Registering Input Devices

}

Application implementation

When the corresponding time response, the user space read event is that the reading is the information of the input_event structure, is no longer a simple number,

In the input_event structure, it already contains information such as type of key, key value code, and so on.

The user needs to input_event the corresponding analysis, obtains the corresponding information.

Struct input_event Ev_key; declaring struct bodies

BUTTON_FD = open ("/dev/event0", O_RDWR);

while (1) {

Count = Read (BUTTON_FD, &ev_key, sizeof (struct input_event));

for (i=0; i< (int) count/sizeof (struct input_event); i++) {

if (Ev_key = = Ev_key.type)//Determine if the type is the same

printf ("type:%d, code:%d, value:%d \ n", ev_key.type,ev_key.code,ev_key.value);

If (Ev_syn = = Ev_key.type)

Printf ("Syn event \ n");

}

}

Close (BUTTON_FD);

We are all on the road, sometimes bitter sometimes sweet, for this I give myself and the same lovers two words: persist.
Together Refueling!!!
January 16, 2015

Linux Input Subsystem Principle Understanding (original)

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.