ReactOS  0.4.13-dev-66-gc714b7f
interrupt.c
Go to the documentation of this file.
1 /*
2  * PROJECT: ReactOS Kernel
3  * LICENSE: GPL - See COPYING in the top level directory
4  * FILE: ntoskrnl/ke/amd64/interrupt.c
5  * PURPOSE: Manages the Kernel's IRQ support for external drivers,
6  * for the purpopses of connecting, disconnecting and setting
7  * up ISRs for drivers. The backend behind the Io* Interrupt
8  * routines.
9  * PROGRAMMERS: Timo Kreuzer (timo.kreuzer@reactos.org)
10  * Alex Ionescu (alex.ionescu@reactos.org)
11  */
12 
13 /* INCLUDES *****************************************************************/
14 
15 #include <ntoskrnl.h>
16 #define NDEBUG
17 #include <debug.h>
18 
20 extern UCHAR KiUnexpectedRange[];
22 void KiInterruptDispatch(void);
23 
24 
25 /* FUNCTIONS ****************************************************************/
26 
27 VOID
28 NTAPI
30  IN PKINTERRUPT Interrupt,
34  IN ULONG Vector,
35  IN KIRQL Irql,
39  IN CHAR ProcessorNumber,
41 {
42 
43  /* Initialize the header */
44  Interrupt->Type = InterruptObject;
45  Interrupt->Size = sizeof(KINTERRUPT);
46 
47  /* If no Spinlock is given, use the internal */
48  if (!SpinLock) SpinLock = &Interrupt->SpinLock;
49  KeInitializeSpinLock(&Interrupt->SpinLock);
50 
51  /* Set the given parameters */
52  Interrupt->ServiceRoutine = ServiceRoutine;
53  Interrupt->ServiceContext = ServiceContext;
54  Interrupt->ActualLock = SpinLock;
55  Interrupt->Vector = Vector;
56  Interrupt->Irql = Irql;
57  Interrupt->SynchronizeIrql = SynchronizeIrql;
58  Interrupt->Mode = InterruptMode;
59  Interrupt->ShareVector = ShareVector;
60  Interrupt->Number = ProcessorNumber;
61  Interrupt->FloatingSave = FloatingSave;
62 
63  /* Set initial values */
64  Interrupt->TickCount = 0;
65  Interrupt->Connected = FALSE;
66  Interrupt->ServiceCount = 0;
67  Interrupt->DispatchCount = 0;
68  Interrupt->TrapFrame = NULL;
69  Interrupt->Reserved = 0;
70 
71  /* Copy the dispatch code (its location independent, no need to patch it) */
72  RtlCopyMemory(Interrupt->DispatchCode,
74  sizeof(Interrupt->DispatchCode));
75 
76  Interrupt->DispatchAddress = 0;
77 }
78 
79 BOOLEAN
80 NTAPI
82 {
83  PVOID CurrentHandler;
84 
85  ASSERT(Interrupt->Vector <= MAXIMUM_IDTVECTOR);
86  ASSERT(Interrupt->Number < KeNumberProcessors);
87  ASSERT(Interrupt->Irql <= HIGH_LEVEL);
88 
89  /* Check if its already connected */
90  if (Interrupt->Connected) return TRUE;
91 
92  /* Query the current handler */
93  CurrentHandler = KeQueryInterruptHandler(Interrupt->Vector);
94 
95  /* Check if the vector is already unused */
96  if ((CurrentHandler >= (PVOID)KiUnexpectedRange) &&
97  (CurrentHandler <= (PVOID)KiUnexpectedRangeEnd))
98  {
99  /* Initialize the list for chained interrupts */
100  InitializeListHead(&Interrupt->InterruptListEntry);
101 
102  /* Set normal dispatch address */
103  Interrupt->DispatchAddress = KiInterruptDispatch;
104 
105  /* Set the new handler */
106  KeRegisterInterruptHandler(Interrupt->Vector,
107  Interrupt->DispatchCode);
108 
109  if (!HalEnableSystemInterrupt(Interrupt->Vector,
110  Interrupt->Irql,
111  Interrupt->Mode))
112  {
113  /* Didn't work, restore old handler */
114  DPRINT1("HalEnableSystemInterrupt failed\n");
115  KeRegisterInterruptHandler(Interrupt->Vector, CurrentHandler);
116  return FALSE;
117  }
118 
119  /* Mark as connected */
120  Interrupt->Connected = TRUE;
121  }
122  else
123  {
124  // later
125  __debugbreak();
126  }
127 
128  return TRUE;
129 }
130 
131 BOOLEAN
132 NTAPI
134 {
136  __debugbreak();
137  return FALSE;
138 }
139 
140 BOOLEAN
141 NTAPI
145 {
147  KIRQL OldIrql;
148 
149  /* Raise IRQL */
150  OldIrql = KfRaiseIrql(Interrupt->SynchronizeIrql);
151 
152  /* Acquire interrupt spinlock */
153  KeAcquireSpinLockAtDpcLevel(Interrupt->ActualLock);
154 
155  /* Call the routine */
157 
158  /* Release lock */
159  KeReleaseSpinLockFromDpcLevel(Interrupt->ActualLock);
160 
161  /* Lower IRQL */
163 
164  /* Return status */
165  return Success;
166 }
#define IN
Definition: typedefs.h:38
BOOLEAN NTAPI HalEnableSystemInterrupt(IN ULONG Vector, IN KIRQL Irql, IN KINTERRUPT_MODE InterruptMode)
Definition: pic.c:295
#define TRUE
Definition: types.h:120
NTSYSAPI VOID NTAPI RtlCopyMemory(VOID UNALIGNED *Destination, CONST VOID UNALIGNED *Source, ULONG Length)
_In_ PKSERVICE_ROUTINE _In_opt_ PVOID _In_opt_ PKSPIN_LOCK _In_ ULONG _In_ KIRQL _In_ KIRQL _In_ KINTERRUPT_MODE InterruptMode
Definition: iofuncs.h:798
UCHAR KiInterruptDispatchTemplate[16]
#define KeLowerIrql(oldIrql)
Definition: env_spec_w32.h:602
UCHAR KiUnexpectedRange[]
_In_ PKSERVICE_ROUTINE _In_opt_ PVOID _In_opt_ PKSPIN_LOCK _In_ ULONG _In_ KIRQL _In_ KIRQL _In_ KINTERRUPT_MODE _In_ BOOLEAN ShareVector
Definition: iofuncs.h:798
char CHAR
Definition: xmlstorage.h:175
VOID NTAPI KeAcquireSpinLockAtDpcLevel(IN PKSPIN_LOCK SpinLock)
Definition: spinlock.c:192
KSPIN_LOCK * PKSPIN_LOCK
Definition: env_spec_w32.h:73
VOID NTAPI KeInitializeInterrupt(IN PKINTERRUPT Interrupt, IN PKSERVICE_ROUTINE ServiceRoutine, IN PVOID ServiceContext, IN PKSPIN_LOCK SpinLock, IN ULONG Vector, IN KIRQL Irql, IN KIRQL SynchronizeIrql, IN KINTERRUPT_MODE InterruptMode, IN BOOLEAN ShareVector, IN CHAR ProcessorNumber, IN BOOLEAN FloatingSave)
Definition: interrupt.c:29
_Out_ PKIRQL Irql
Definition: csq.h:179
void __cdecl __debugbreak(void)
Definition: intrin_ppc.h:698
FORCEINLINE PVOID KeQueryInterruptHandler(IN ULONG Vector)
Definition: ke.h:268
KSERVICE_ROUTINE * PKSERVICE_ROUTINE
Definition: ketypes.h:500
_In_ PKSERVICE_ROUTINE _In_opt_ PVOID _In_opt_ PKSPIN_LOCK SpinLock
Definition: iofuncs.h:798
UCHAR KIRQL
Definition: env_spec_w32.h:591
NTSTATUS(* NTAPI)(IN PFILE_FULL_EA_INFORMATION EaBuffer, IN ULONG EaLength, OUT PULONG ErrorOffset)
Definition: IoEaTest.cpp:117
FORCEINLINE VOID KeInitializeSpinLock(_Out_ PKSPIN_LOCK SpinLock)
Definition: kefuncs.h:251
unsigned char BOOLEAN
smooth NULL
Definition: ftsmooth.c:416
enum _KINTERRUPT_MODE KINTERRUPT_MODE
_In_ PKSERVICE_ROUTINE _In_opt_ PVOID _In_opt_ PKSPIN_LOCK _In_ ULONG _In_ KIRQL _In_ KIRQL SynchronizeIrql
Definition: iofuncs.h:798
KSYNCHRONIZE_ROUTINE * PKSYNCHRONIZE_ROUTINE
Definition: ketypes.h:863
#define MAXIMUM_IDTVECTOR
Definition: asm.h:277
KIRQL FASTCALL KfRaiseIrql(IN KIRQL NewIrql)
Definition: pic.c:187
_In_ PKSYNCHRONIZE_ROUTINE SynchronizeRoutine
Definition: kefuncs.h:549
VOID NTAPI KeReleaseSpinLockFromDpcLevel(IN PKSPIN_LOCK SpinLock)
Definition: spinlock.c:215
BOOLEAN NTAPI KeConnectInterrupt(IN PKINTERRUPT Interrupt)
Definition: interrupt.c:81
_In_ PKSERVICE_ROUTINE _In_opt_ PVOID ServiceContext
Definition: iofuncs.h:798
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
unsigned char UCHAR
Definition: xmlstorage.h:181
_Requires_lock_held_ Interrupt _Releases_lock_ Interrupt _In_ _IRQL_restores_ KIRQL OldIrql
Definition: kefuncs.h:803
_In_ PKSERVICE_ROUTINE _In_opt_ PVOID _In_opt_ PKSPIN_LOCK _In_ ULONG _In_ KIRQL _In_ KIRQL _In_ KINTERRUPT_MODE _In_ BOOLEAN _In_ KAFFINITY _In_ BOOLEAN FloatingSave
Definition: iofuncs.h:798
BOOLEAN NTAPI KeDisconnectInterrupt(IN PKINTERRUPT Interrupt)
Definition: interrupt.c:133
CCHAR KeNumberProcessors
Definition: krnlinit.c:35
FORCEINLINE VOID KeRegisterInterruptHandler(IN ULONG Vector, IN PVOID Handler)
Definition: ke.h:242
_In_ PKSYNCHRONIZE_ROUTINE _In_opt_ __drv_aliasesMem PVOID SynchronizeContext
Definition: kefuncs.h:549
#define HIGH_LEVEL
Definition: env_spec_w32.h:703
_In_ PKSERVICE_ROUTINE _In_opt_ PVOID _In_opt_ PKSPIN_LOCK _In_ ULONG Vector
Definition: iofuncs.h:798
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
UCHAR KiUnexpectedRangeEnd[]
#define DPRINT1
Definition: precomp.h:8
#define OUT
Definition: typedefs.h:39
struct _KINTERRUPT KINTERRUPT
unsigned int ULONG
Definition: retypes.h:1
#define UNIMPLEMENTED
Definition: debug.h:114
BOOLEAN NTAPI KeSynchronizeExecution(IN OUT PKINTERRUPT Interrupt, IN PKSYNCHRONIZE_ROUTINE SynchronizeRoutine, IN PVOID SynchronizeContext OPTIONAL)
Definition: interrupt.c:142
void KiInterruptDispatch(void)
_In_ PKSERVICE_ROUTINE ServiceRoutine
Definition: iofuncs.h:798
PULONG MinorVersion OPTIONAL
Definition: CrossNt.h:68