Uninformed: Informative Information for the Uninformed

Vol 3» 2006.Jan

Direct IRQL Adjustment

Type: R0 IRQL Migrator
Size: 6 bytes
Compat: All

One of the most straight-forward approaches that can be taken to migrate a payload to a safe IRQL is to directly lower a processor's IRQL. This approach was first proposed by eEye and involved resolving and calling hal!KeLowerIrql with the desired IRQL, such as PASSIVE_LEVEL[2]. This technique is very dangerous due to the way in which IRQLs are intended to be used. The direct lowering of an IRQL can lead to machine deadlocks and crashes due to unsafe assumptions about locks being held, among other things. An optimization to the hal!KeLowerIrql technique is to perform the operation that hal!KeLowerIrql actually performs. Specifically, hal!KeLowerIrql is a simple wrapper for hal!KfLowerIrql which adjusts the Irql attribute of the KPCR structure for a specific processor to the supplied IRQL (as well as calling software interrupt handlers for masked IRQLs). To implement a payload that migrates to a safe IRQL, all that is required is to adjust the value at fs:0x24, such as by lowering it to PASSIVE_LEVEL as shown below4.1.

00000000  31C0              xor eax,eax
00000002  64894024          mov [fs:eax+0x24],eax

One concern about taking this approach over calling hal!KeLowerIrql is that the soft-interrupt handlers associated with interrupts that were masked while at a raised IRQL will not be called. It is unclear whether or not this could lead to a deadlock, but is theorized that the answer could be yes. However, the authors did test writing a driver that raised to HIGH_LEVEL, spun for a period of time (during which kb/mouse interrupts were sent), and then manually adjusted the IRQL as described above. There appeared to be no adverse side effects, but it has not been ruled out that a deadlock could be possible4.2.

Aside from the risks, this approach is nice because it is very small (6 bytes), so assuming there are no significant problems with it, then the use of this method would be a no-brainer given the right set of circumstances for a vulnerability.