Allow shared interrupts.

svn path=/trunk/; revision=39720
This commit is contained in:
Dmitry Gorbachev 2009-02-23 13:16:43 +00:00
parent cb2ab2abe6
commit 50ee6815d3
4 changed files with 85 additions and 7 deletions

View file

@ -227,12 +227,13 @@ Author:
//
// KINTERRUPT Offsets
//
#define KINTERRUPT_INTERRUPT_LIST_HEAD 0x04
#define KINTERRUPT_SERVICE_ROUTINE 0x0C
#define KINTERRUPT_SERVICE_CONTEXT 0x10
#define KINTERRUPT_TICK_COUNT 0x18
#define KINTERRUPT_ACTUAL_LOCK 0x1C
#define KINTERRUPT_IRQL 0x20
#define KINTERRUPT_VECTOR 0x24
#define KINTERRUPT_IRQL 0x28
#define KINTERRUPT_SYNCHRONIZE_IRQL 0x29
#define KINTERRUPT_DISPATCH_COUNT 0x38

View file

@ -1334,7 +1334,7 @@ VfOvr_&Label:
mov [edi+KINTERRUPT_TICK_COUNT], eax
jmp VfRstDef_&Label
.1:
1:
/* Check if the debugger is enabled */
cmp byte ptr __KdDebuggerEnabled, 0
jnz 1f

View file

@ -281,13 +281,17 @@ KeConnectInterrupt(IN PKINTERRUPT Interrupt)
(Dispatch.Interrupt->Mode == Interrupt->Mode))
{
/* The vector is shared and the interrupts are compatible */
ASSERT(FALSE); // FIXME: NOT YET SUPPORTED/TESTED
Interrupt->Connected = Connected = TRUE;
ASSERT(Irql <= SYNCH_LEVEL);
/* FIXME */
// ASSERT(Irql <= SYNCH_LEVEL);
/* Check if this is the first chain */
if (Dispatch.Type != ChainConnect)
{
/* This is not supported */
ASSERT(Dispatch.Interrupt->Mode != Latched);
/* Setup the chainned handler */
KiConnectVectorToInterrupt(Dispatch.Interrupt, ChainConnect);
}

View file

@ -2533,8 +2533,81 @@ TRAP_FIXUPS kit_a, kit_t, DoFixupV86, DoFixupAbios
.func KiChainedDispatch2ndLvl@0
_KiChainedDispatch2ndLvl@0:
/* Not yet supported */
UNHANDLED_PATH
NextSharedInt:
/* Raise IRQL if necessary */
mov cl, [edi+KINTERRUPT_SYNCHRONIZE_IRQL]
cmp cl, [edi+KINTERRUPT_IRQL]
je 1f
call @KfRaiseIrql@4
1:
/* Acquire the lock */
mov esi, [edi+KINTERRUPT_ACTUAL_LOCK]
GetIntLock2:
ACQUIRE_SPINLOCK(esi, IntSpin2)
/* Make sure that this interrupt isn't storming */
VERIFY_INT kid2
/* Save the tick count */
mov esi, _KeTickCount
/* Call the ISR */
mov eax, [edi+KINTERRUPT_SERVICE_CONTEXT]
push eax
push edi
call [edi+KINTERRUPT_SERVICE_ROUTINE]
/* Save the ISR result */
mov bl, al
/* Check if the ISR timed out */
add esi, _KiISRTimeout
cmp _KeTickCount, esi
jnc ChainedIsrTimeout
ReleaseLock2:
/* Release the lock */
mov esi, [edi+KINTERRUPT_ACTUAL_LOCK]
RELEASE_SPINLOCK(esi)
/* Lower IRQL if necessary */
mov cl, [edi+KINTERRUPT_IRQL]
cmp cl, [edi+KINTERRUPT_SYNCHRONIZE_IRQL]
je 1f
call @KfLowerIrql@4
1:
/* Check if the interrupt is handled */
or bl, bl
jnz 1f
/* Try the next shared interrupt handler */
mov eax, [edi+KINTERRUPT_INTERRUPT_LIST_HEAD]
lea edi, [eax-KINTERRUPT_INTERRUPT_LIST_HEAD]
jmp NextSharedInt
1:
ret
#ifdef CONFIG_SMP
IntSpin2:
SPIN_ON_LOCK(esi, GetIntLock2)
#endif
ChainedIsrTimeout:
/* Print warning message */
push [edi+KINTERRUPT_SERVICE_ROUTINE]
push offset _IsrTimeoutMsg
call _DbgPrint
add esp,8
/* Break into debugger, then continue */
int 3
jmp ReleaseLock2
/* Cleanup verification */
VERIFY_INT_END kid2, 0
.endfunc
.func KiChainedDispatch@0
@ -2599,8 +2672,8 @@ _KiInterruptDispatch@0:
jz SpuriousInt
/* Acquire the lock */
GetIntLock:
mov esi, [edi+KINTERRUPT_ACTUAL_LOCK]
GetIntLock:
ACQUIRE_SPINLOCK(esi, IntSpin)
/* Make sure that this interrupt isn't storming */