VBox,Virtual PC,VMware i IDT Hooking

It’s gonna be quite light version of post about “anomaly” which I had pleasure to notice during tests of IDT hooking under virtual machines mentioned in this post title. Why light? Because in order to present all details related with cases that I’m going to show in letter part of post, it would required a deeply research regarding to internal manner of work each virtual machine
( I guess so :P). My suggestion is to treat this post like a curiosity/(vector to research) and not like a result of deeply research.

Entire story begins from the moment when I decided to test the simplest hook on KiSystemService procedure through modification its address in IDT table. It’s a piece of code responsible of hook installation:

void IDTHook()
{
IDTINFO idtInfo;
IDTENTRY *idt_entries;
IDTENTRY *int2e_entry;
DbgPrint([+] IDTHook);
//pobranie IDTINFO
idtInfo = getIDTInfo();
//pobranie *tablicy IDT
idt_entries = getIDTEntries(&idtInfo);

//zapisanie oryginalnego IDTENTRY_2E
orgIDTEntry_2e = idt_entries[KiSystemService_INDEX];
//zapisanie DWORD'a na potrzeby funkcji hookujacej
orgKiSystemService = MAKELONG(orgIDTEntry_2e.LowOffset,orgIDTEntry_2e.HiOffset);
__asm cli;//wylacz obsluge maskowalnych przerwan
idt_entries[KiSystemService_INDEX].LowOffset = (unsigned short)(&MySystemService);
idt_entries[KiSystemService_INDEX].HiOffset  = (unsigned short)(((unsigned long)(&MySystemService))<<16);
__asm lidt idtInfo;
__asm sti;//wlacz obsluge maskowalnych przerwan

}

‘code MySystemService has been rewritten from „Subverting Windows Kernel”‘

__declspec(naked) MySystemService()
{

__asm{
pushad
pushfd
push fs
mov bx,0x30
mov fs,bx
push ds
push es
//do something

//Finish:
pop es
pop ds
pop fs
popfd
popad

jmp	orgKiSystemService;
}
}
/* __asm { sysenter VPC } */

Without bigger doubts and not necessary thinking I decided to test obtained driver under
Virtual PC(ver. 6.0.192.0 + additions)[OS: Windows XP SP3 Eng], which I mostly used to use. To my great surprise (because I counted on BSOD:P) during attempt to hook installation, occurred internal VPC error:
vpc_crash_error

Hymm…strange issue I thought. Meanwhile I remind to myself that operation system doesn’t need to use IDT table if our processor supports sysenter/syscall instruction. Eye throw under vpc on call to one of mostly used native api: ZwOpenFile, dispelled my doubts:
vpc_syscalls_handler

Error “triggered” by VPC pointed that it’s not strict related problem with OS, rather with vm, and now additionally we know that sense of hook installation on IDT under VPC isn’t too big(by what should be harmless) ;). I decided to perform test again after uninstallation additions from system. Another surprise here, system acted like it should act, that is:
– hook have been installed successfully
and neither of breakpoints (after quite long time), which I had set on MySystemService wasn’t triggered. We will see now how to cases look under VirtualBox.

/* __asm { INT VirtualBox } */

Ver. 3.0.8 r53138 + additions
OS stays without changes under each vm.

First issue which I have checked under this vm is manner on what process steps from r3 to r0.
vbox_syscalls_handler

Delicious! Like you can see on attached screenshot without any doubts we can test hooks on IDT. It seemed as such to me …
I’m loading driver ,I’m passing proper IOCTL code to my driver which is going to trigger hook installation and … :

vbox_crash

entire action is ending with unexpected VBox crash.
Don’t wondering too much I have uninstalled additions from system and I repeated test. Success! Hook installation have been made without any problems, but after couple another attempts I’ve had situations where system crashed with BSOD unambiguously saying, that occurred access attempt to paged memory region. Windbg was pointing following line of code as source of all evil:

idt_entries[KiSystemService_INDEX].LowOffset = (unsigned short)(&MySystemService);

Hymm…a little strange. IDT in paged memory region o_0 ?
I have modified a little source code to eliminate this problem by mapping IDT table under NON-PAGED memory area. Code presents now in the following way :

void IDTHook()
{
IDTINFO idtInfo;
IDTENTRY *idt_entries;
IDTENTRY *int2e_entry;
DbgPrint("[+] IDTHook");
//pobranie IDTINFO
idtInfo = getIDTInfo();
//pobranie *tablicy IDT
idt_entries = getIDTEntries(&idtInfo);

//try to map it
idt_entries = mapMemory(idt_entries,idtInfo.IDTLimit);// NOWA LINIA
//update idtinfo struct
idtInfo.HiIDTbase  = HIWORD(idt_entries);
idtInfo.LowIDTbase = LOWORD(idt_entries);

//zapisanie oryginalnego IDTENTRY_2E
orgIDTEntry_2e = idt_entries[KiSystemService_INDEX];
//zapisanie DWORD'a na potrzeby funkcji hookujacej
orgKiSystemService = MAKELONG(orgIDTEntry_2e.LowOffset,orgIDTEntry_2e.HiOffset);
__asm cli;//wylacz obsluge maskowalnych przerwan
idt_entries[KiSystemService_INDEX].LowOffset = (unsigned short)(&MySystemService);
idt_entries[KiSystemService_INDEX].HiOffset  = (unsigned short)(((unsigned long)(&MySystemService))>>16);
__asm lidt idtInfo;
__asm sti;//wlacz obsluge maskowalnych przerwan

}

This simple “patch” eliminated occurrence of BSOD’s.

/* __asm { VMware sysenter } */

VMware Workstation
6.5.3 build-185404

Quick look on transition r3 – > r0:
vmware_syscalls_handler
As we can see sysenter has been used here. I won’t dwell on vmware and at the beginning I’m going to say that there is no problems with hook installation, with or without installed additions in system.

As summary I prepared the following table:
table

Like always comments and any kind of suggestions are welcome ;).

This entry was posted in Analiza and tagged , , , , , , , . Bookmark the permalink.

4 Responses to VBox,Virtual PC,VMware i IDT Hooking

  1. pi3 says:

    Moze jakis 0day? :>

  2. Icewall says:

    @pi3
    Stosując powściągliwość emocjonalną nazwę to poprostu usterką 😛

  3. Gynvael says:

    Thx za tabelkę, przyda się ;>
    Jestem ciekaw na czym bug polega głębiej, i czy można go ztriggerować z user mode (np wysyłając jakieś przerwanie).

  4. Icewall says:

    @Gynvael
    n/p ; )
    Mhmm trzeba będzie przysiąść i zbadać ;).