- Overview: The system must be aware of the state of the hardware in a timely manner, usually in two ways: one is polling, and the other is by responding to hardware interrupts. The former will waste processor time, while the latter will not.
- Prepare the and the mouth
- The same port is not interrupted until no section is set to produce an interrupt
- The standard set of the same port 2 (px37a, 0x27a, or other ports) will enable interrupt reporting for the 4th bit, 0x10
- When the interrupt state is enabled, the port generates an interrupt whenever the level of pin 10 changes from low to high
- Pin 9 is the highest bit in the data byte of the same port
- Install Interrupt handling Routines
- Interrupt signal line is a very precious and limited resource
- The kernel maintains a registry of interrupt signal lines similar to the I/O port registry
- The module requests an interrupt channel before using the interrupt, and then releases the channel after use
- <linux/sched.h>
- int REQUEST_IRQ (unsigned int IRQ, irqreturn_t (*handler) (int, void *, struct pt_regs *), unsigned long flags, const char *dev_name, void *dev_id);
- Return 0 indicates successful application
- Flags
- Sa_interrupt
- Indicates that this is a "fast" interrupt processing routine
- Sa_shirq
- Indicates that interrupts can be shared between devices
- Sa_sample_random
- Indicates that the resulting interrupt can contribute to the entropy pool (entropy pools) used by/dev/random devices and/dev/urandom devices
- void Free_irq (unsigned int irq, void *dev_id);
- int CAN_REQUEST_IRQ (unsigned int IRQ, unsigned long flags);
- The correct location for using REQUEST_IRQ should be before the device is first opened, and the hardware is told to produce an interrupt
- The location of the call to Free_irq is the last time the device was shut down and the hardware was told not to interrupt the processor
- /proc interface
- /proc/interrupts
- Not dependent on architecture
- /proc/stat
- The number of interrupts defined on the current x86 architecture is 224 and can be explained from the Include/asm-386/irq.h file
- Automatically detect IRQ numbers
- Probes with the help of the kernel
- <linux/interrupt.h>
- unsigned long probe_irq_on (void);
- int Probe_irq_off (unsigned long);
- DIY detection
- Fast and slow processing routines
- When fast interrupt execution, all other interrupts on the current processor are disabled
- Inside of interrupt processing on x86 platform
- Arch/i386/kernel/irq.c
- Arch/i386/kernel/apic.c
- Arch/i386/kernel/entry. S
- Arch/i386/kernel/i8259.c
- Include/asm-i386/hw_irq.h
- IRQ detection is done by setting the irq_waiting status bit for each IRQ that lacks interrupt handling routines.
- Implementing an interrupt processing routine
- The interrupt processing routine runs within the break time, so its behavior is subject to some limitations
- Cannot send or receive data to user space
- Do not affectation any action that may occur during hibernation
- Cannot call Schdule function
- Receive feedback about interrupts to the device and read or write the data according to the different meanings of the interrupt being served
- Usually do clear a bit on the interface card, most hardware devices will not produce additional interrupts until their "interrupt-pending (interrupt suspend)" bit is cleared
- A typical task for an interrupt-handling routine is to wake up a process that is dormant on a device if the interrupt notifies the process that an event has occurred, such as a new data arrival.
- Parameters and return values for processing routines
- An int IRQ is an interrupt number
- Void *dev_id is a type of customer data (that is, private data that is available to the driver)
- struct Pt_reg *regs is seldom used, it holds the processor context snapshot before the processor enters the interrupt code
- The interrupt processing routine should return a value that indicates whether an interrupt was actually handled, and if the processing routine finds that its device does need to be processed, it should return irq_handled, otherwise the return value should be Irq_none
- Enable and disable interrupts
- sometimes device drivers must block interrupts during a time period, such as blocking interrupts when owning a spin lock
- disabling a single interrupt
- <asm/irq.h>
- void Disable_irq (int IRQ);
- void Disable_irq_nosync (int IRQ);
- void Enable_irq (int IRQ);
The
- DIABLES_IRQ not only disables a given interrupt, but also waits for the currently executing interrupt-handling routine to complete
- if the thread that calls DISABLE_IRQ has any resources (such as spin locks) that are required by the interrupt-processing routines. The system will deadlock
- Disable all interrupts
- <asm/system.h>
- void Local_irq_save (Unsig Ned long FALSG);
- void local_irq_disable (void);
- void Local_irq_restore (unsigned long flags);
- void local_irq_enable (void)
- top half and bottom half
- top half, is the actual response interrupt routine, that is, the interrupt routine registered with REQUEST_IRQ
- , is a routine that is dispatched by the top half and executed in a later, more secure time
- when the bottom half is processed When a routine executes, all interrupts are open
- Typically, the top half holds the device's data to a device-specific buffer and dispatches its bottom half
- tasklet
- Tasklet can be scheduled to run multiple times, but TASKL The ET's schedule does not accumulate
- if the driver has more than one tasklet, you must use some kind of locking mechanism to avoid conflicts with each other
- tasklet ensure that the function that first dispatched them runs on the same CPU
- must use Macro Declare_tasklet declaration Tasklet
- Declare_tasklet (name, function, data);
- void Do_tasklet (unsigned long);
- Declare_tasklet (Test_tasklet, Do_tasklet, 0);
- Tasklet_schedule ($test _tasklet);
- Work Column
- Task Force column functions run in the context of a process, so you can hibernate if necessary
- cannot copy data from the working queue to user space
/li>
- interrupt sharing
- IRQ Beacon line on PC cannot serve more than one device
- modern hardware has been able to 谲诈 interrupted shares, the PCI bus requires peripherals to share interrupts
- install shared processing routines
li> shared interrupts are also installed through REQUEST_IRQ, but there are two different
- request interrupts, you must specify the SA_SHIRQ bit
- dev_id parameter in the flags parameter must be unique, any point to the module address A pointer to a space can be used, but dev_id cannot be set to null
- If one of the following conditions is met, then REQUEST_IRQ will succeed
- interrupt signal line NULL Idle
- Any processing routines that have registered the interrupt signal line also identify that the IRQ is shared
- drivers that use shared processing routines need to be careful about one thing: you can't use ENABLE_IRQ and disable_i RQ
- Run processing routine
- all registered processing routines are called when the kernel receives an interrupt
- a shared interrupt processing routine must be able to differentiate between interrupts to be processed and interrupts generated by other devices From
- /proc interface and shared interrupts
- installing shared interrupt handling routines on the system does not affect/proc/stat, and it does not even know which processing routines are shared, but/proc/inter Rupts will change slightly
- Interrupt-driven I/O
- If data transfer to and from the driver-managed hardware is delayed for some reason, the driver author should implement buffering
- Data buffers help to separate the delivery and reception of data from the system call write and read, thereby improving the overall performance of the system
- A good buffering mechanism requires interrupt-driven I/O
- To properly interrupt-driven data transfer, the hardware should be able to generate interrupts according to the following semantics
- For input, the device interrupts the processor when new data has arrived and the processor is ready to receive it
- For output, interrupts are emitted when the device is ready to receive new data or respond to a successful data transfer
The tenth chapter of Linux Device Drivers interrupts processing--note