IoConnectInterruptEx
NTSTATUS __stdcall IoConnectInterruptEx(PIO_CONNECT_INTERRUPT_PARAMETERS Parameters){
ULONG Version;
NTSTATUS v3;
KIRQL v4;
KIRQL Irql;
char v6;
USHORT Group;
int v8;
PVOID v9;
unsigned int v10;
__int64 v11;
KIRQL v12;
__int128 v13;
__m128i v14;
__int128 v15;
__int128 v16;
NTSTATUS v17;
KAFFINITY ProcessorEnableMask;
KSPIN_LOCK *v20;
PKSERVICE_ROUTINE ServiceRoutine;
KSERVICE_ROUTINE *PhysicalDeviceObject;
PKINTERRUPT *InterruptObject;
PKSPIN_LOCK ServiceContext;
ULONG SpinLock;
KIRQL SynchronizeIrql;
KINTERRUPT_MODE InterruptMode;
KINTERRUPT_MODE ShareVector;
struct _GROUP_AFFINITY *TargetProcessors;
BOOL v30[4];
int v31;
_BYTE result[20];
__int128 v33;
__int128 v34;
__int128 v35;
__int128 v36;
__int64 v37;
PVOID P;
__int64 v39;
P = 0i64;
v39 = 0i64;
if( KeGetCurrentIrql() )
KeBugCheckEx(0x121u, 1ui64, KeGetCurrentIrql(), 0i64, 0i64);
Version = Parameters->Version;
switch( Version )
{
case 1u:
goto LABEL_49;
case 2u:
return IopConnectLineBasedInterrupt();
case 3u:
goto LABEL_5;
case 4u:
LABEL_49:
if( !Parameters->FullySpecified.PhysicalDeviceObject )
return -1073741811;
if( !Parameters->FullySpecified.ServiceRoutine )
return -1073741811;
v4 = Parameters->FullySpecified.SynchronizeIrql;
Irql = Parameters->FullySpecified.Irql;
if( v4 < Irql )
return -1073741811;
if( v4 || Irql )
{
v6 = 0;
}
else
{
v6 = 1;
if( Parameters->FullySpecified.SpinLock )
return -1073741811;
}
if( Version == 4 )
Group = Parameters->FullySpecified.Group;
else
Group = 0;
IopGetInterruptConnectionData(Parameters->FullySpecified.PhysicalDeviceObject, &P);
if( v8 >= 0 )
{
memset((INT64)result, 0i64);
v9 = P;
v10 = 0;
v31 = 0;
if( *(_DWORD *)P )
{
while( 1 )
{
v11 = 88i64 * v10;
if( *(_DWORD *)((char *)P + v11 + 12) == Parameters->FullySpecified.Vector )
{
v12 = Parameters->FullySpecified.Irql;
if( (*((_BYTE *)P + v11 + 16) == v12 || !v12)
&& *(_DWORD *)((char *)P + v11 + 24) == Parameters->FullySpecified.InterruptMode
&& *(_WORD *)((char *)P + v11 + 40) == Group
&& *(_QWORD *)((char *)P + v11 + 32) == Parameters->FullySpecified.ProcessorEnableMask )
{
break;
}
}
if( ++v10 >= *(_DWORD *)P )
goto LABEL_42;
}
v31 = 1;
v13 = *(_OWORD *)((char *)P + 88 * v10 + 40);
v14 = *(__m128i *)((char *)P + 88 * v10 + 8);
v33 = *(_OWORD *)((char *)P + 88 * v10 + 24);
v15 = *(_OWORD *)((char *)P + 88 * v10 + 56);
v34 = v13;
v16 = *(_OWORD *)((char *)P + 88 * v10 + 72);
v35 = v15;
*(_QWORD *)&v15 = *((_QWORD *)P + 11 * v10 + 11);
*(__m128i *)&result[4] = v14;
v37 = v15;
v36 = v16;
if( !_mm_cvtsi128_si32(v14) && (BYTE12(v35) & 1) != 0 )
Parameters->FullySpecified.ShareVector = 1;
v17 = IopConnectInterrupt(
&v39,
(ULONG_PTR)Parameters->FullySpecified.PhysicalDeviceObject,
(__int64(__fastcall *)(__int64, __int64))Parameters->FullySpecified.ServiceRoutine,
0i64,
(__int64)Parameters->FullySpecified.ServiceContext,
0,
(__int64)Parameters->FullySpecified.SpinLock,
Parameters->FullySpecified.SynchronizeIrql,
Parameters->FullySpecified.ShareVector,
(__int64)TargetProcessors,
(__int64)&v31);
if( v17 >= 0 )
*Parameters->FullySpecified.InterruptObject = (PKINTERRUPT)(v39 + 112);
ExFreePoolWithTag(v9, 0);
return v17;
}
LABEL_42:
ExFreePoolWithTag(P, 0);
return -1073741637;
}
if( v6 )
return -1073741637;
ProcessorEnableMask = Parameters->FullySpecified.ProcessorEnableMask;
v20 = (KSPIN_LOCK *)Parameters->FullySpecified.ServiceContext;
ServiceRoutine = Parameters->FullySpecified.ServiceRoutine;
PhysicalDeviceObject = (KSERVICE_ROUTINE *)Parameters->FullySpecified.PhysicalDeviceObject;
InterruptObject = Parameters->FullySpecified.InterruptObject;
*(_QWORD *)&v30[2] = 0i64;
*(_QWORD *)v30 = ProcessorEnableMask;
LOBYTE(TargetProcessors) = Parameters->FullySpecified.ShareVector;
ShareVector = Parameters->FullySpecified.InterruptMode;
LOBYTE(InterruptMode) = Parameters->FullySpecified.SynchronizeIrql;
SynchronizeIrql = Parameters->FullySpecified.Irql;
SpinLock = Parameters->FullySpecified.Vector;
ServiceContext = Parameters->FullySpecified.SpinLock;
LOWORD(v30[2]) = Group;
return IopConnectInterruptFullySpecified(
InterruptObject,
PhysicalDeviceObject,
ServiceRoutine,
v20,
(UINT32)ServiceContext,
SpinLock,
SynchronizeIrql,
InterruptMode,
ShareVector,
TargetProcessors,
(BOOL)v30);
}
if( Version != 5 )
{
Parameters->Version = 3;
return -1073741637;
}
LABEL_5:
v3 = IopConnectMessageBasedInterrupt(
Version,
Parameters->FullySpecified.PhysicalDeviceObject,
Parameters->MessageBased.ConnectionContext.InterruptMessageTable,
Parameters->MessageBased.MessageServiceRoutine,
Parameters->FullySpecified.ServiceContext,
Parameters->FullySpecified.SpinLock,
Parameters->FullySpecified.SynchronizeIrql,
InterruptMode);
if( v3 < 0 )
{
if( Parameters->MessageBased.FallBackServiceRoutine )
{
v17 = IopConnectLineBasedInterrupt();
Parameters->Version = 2;
return v17;
}
return -1073741637;
}
return v3;
}Referenced by:
HalpInterruptConnect