Quantcast
Channel: 看雪安全论坛
Viewing all articles
Browse latest Browse all 9556

技术专题 【分享】Win XP/7/8 下 32/64-Bit 枚举多处理器 IDT

$
0
0
网上枚举多核IDT的代码或多或少都有些问题,以下代码在WinXP 32-Bit、Win7 32/64-Bit、Win8 32/64-Bit测试通过。
//
#define HGMAKESIZE (a, b) (( ULONG64)(((ULONG32 )(((ULONG64)( a)) & 0xFFFFFFFF)) | ((ULONG64)((ULONG32 )(((ULONG64)( b)) & 0xFFFFFFFF))) << 32))
//
// Define struct
//
typedef struct _HG_IDT_ENTRY
{
unsigned short LowOffset;
unsigned short selector;
unsigned char unused_lo;
unsigned char segment_type:4; // 0x0E is an interrupt gate
unsigned char system_segment_flag:1;
unsigned char DPL:2; // descriptor privilege level
unsigned char P:1; // present
#if defined (_WIN64)
UINT16 MidOffset ;
ULONG32 HiOffset ;
ULONG32 Placeholder ; // not use
#else
unsigned short HiOffset;
#endif
} HG_IDT_ENTRY, * PHG_IDT_ENTRY ;

//
// sidt return idt in this format
// Stores the interrupt descriptor table register (IDTR) in the destination operand. In legacy and
// compatibility mode, the destination operand is 6 bytes; in 64-bit mode it is 10 bytes. In all modes,
// operand-size prefixes are ignored.
// In non-64-bit mode, the lower two bytes of the operand specify the 16-bit limit and the upper 4 bytes
// specify the 32-bit base address.
// In 64-bit mode, the lower two bytes of the operand specify the 16-bit limit and the upper 8 bytes
// specify the 64-bit base address.
//
#pragma pack (1)
typedef struct _HG_IDT_INFO
{
unsigned short IDTLimit;
#if defined (_WIN64)
ULONG32 LowIDTbase ;
ULONG32 HiIDTbase ;
#else
unsigned short LowIDTbase;
unsigned short HiIDTbase;
#endif
}HG_IDT_INFO, * PHG_IDT_INFO;
#pragma pack ()

typedef ULONG (NTAPI * pfnKeQueryActiveProcessorCount)(PKAFFINITY ActiveProcessors);

KEVENT g_Event ;
ULONG_PTR g_CurrentCpuAffinity = 0;

//
// Private methods
//
VOID TraverseIdt (ULONG_PTR CpuOrdinal)
{
HG_IDT_INFO idt ;
SIZE_T i = 0;
SIZE_T address = 0;
PHG_IDT_ENTRY idt_entry = NULL;
PHG_IDT_ENTRY idtTmp = NULL;

#if defined (_WIN64)
__sidt(&idt );
idt_entry = (PHG_IDT_ENTRY )HGMAKESIZE( idt.LowIDTbase , idt.HiIDTbase );
#else
_asm{
sidt idt
}
idt_entry = (PHG_IDT_ENTRY )MAKELONG( idt.LowIDTbase , idt.HiIDTbase );
#endif

if (idt_entry )
{
for (i = 0; i <= 0xFF; i++)
{
idtTmp = &idt_entry [i];
#if defined (_WIN64)
address = HGMAKESIZE (MAKELONG( idtTmp->LowOffset , idtTmp-> MidOffset), idtTmp->HiOffset );
#else
address = MAKELONG (idtTmp-> LowOffset, idtTmp->HiOffset );
#endif
IdtLog(("CPU Ordinal: %d, Index: %02X, Address: %p\n" , CpuOrdinal, i , address));
}
}
}

VOID TraverseIdtDpc (
__in struct _KDPC * Dpc,
__in ULONG DeferredContext,
__in PVOID SystemArgument1,
__in PVOID SystemArgument2)
{
HG_IDT_INFO idt ;
SIZE_T i = 0;
SIZE_T address = 0;
PHG_IDT_ENTRY idt_entry = NULL;
PHG_IDT_ENTRY idtTmp = NULL;

TraverseIdt(g_CurrentCpuAffinity );

HgKeSetEvent(&g_Event , IO_NO_INCREMENT, FALSE);
}

VOID QueryCurrentIdt ()
{
KAFFINITY CpuAffinity ;
size_t nCpuCount = 0;
size_t i = 0;
KDPC Dpc ;

CpuAffinity = HgKeQueryActiveProcessors ();

for(i = 0; i < sizeof(KAFFINITY ); i ++){
if ((CpuAffinity >> i) & 1){
nCpuCount ++;
}
}

if (nCpuCount == 1){
KIRQL OldIrql = KeRaiseIrqlToDpcLevel();
TraverseIdt(0);
KeLowerIrql(OldIrql );
} else{
for(i = 0; i < sizeof(KAFFINITY ); i ++){
if ((CpuAffinity >> i) & 1){
g_CurrentCpuAffinity = i ;
HgKeInitializeEvent(&g_Event , NotificationEvent, FALSE);
HgKeInitializeDpc(&Dpc , (PKDEFERRED_ROUTINE )TraverseIdtDpc, NULL);
HgKeSetTargetProcessorDpc(&Dpc , (CCHAR) i);
HgKeSetImportanceDpc(&Dpc , HighImportance);
HgKeInsertQueueDpc(&Dpc , NULL, NULL);

if (HgKeWaitForSingleObject (&g_Event, (KWAIT_REASON)0, 0, 0, 0) == STATUS_SUCCESS )
{
continue;
}
}
}
}
}

Win7 64-Bit部分截图:

附件 82160

上传的图像
文件类型: png idt.png (15.4 KB)

Viewing all articles
Browse latest Browse all 9556

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>