x86 or x64 or independent? Which SLIC? Can you share the secret of creating the patch (ie change the SLIC etc)? sebus
I tried different decompiler such as Boomerang and PVDasm. But both are unable to open the dll. If you do a binary compare, the you'll see that there a so many changed bytes, so i think it was done by a tool and not manual. But i didn't know yet, which tool is used. Obelix
i just read through all pages on this thread but since i am a noob, do not understand a word of it. is it possible to activate Win7 in VBox? my host has SLIC 2.1. thanks for reading such a noob question. EDIT: N/M .. i found a way for VMWare and i'll just use that , thanks
Unfortunately the patch wasn't made by a tool. I had to do it all by myself Right now i'm busy in doing a clean install on my (preloaded) notebook, so i'll later tell you the details. I used Tiny Hexer, PE Explorer and Olly Debugger. You should be able to patch other SLICs and strings into the modded one (they are all the same length). 64 bit should be possible, too (little bit more work to do). You should have at least basic knowledge in assembler plus a little bit of reading here or there It involves: changing a couple of strings, adding a SLIC, adding code to load the SLIC, plus a few minor tweaks (new relocation entry, segment length ...).
I don't know, how to use the PE Explorer properly. I have understand the following: I'am using VBoxDD.dll from Version 3.1.4 as example: 1. You have to insert the SLIC at 194E80h 2. You have to insert the code, which is loading the SLIC, into 92860h 3. You need to jump in the new code at 17B82-5h change the Bytes to E8 D9 AC 07 (which means: jmp 92860h) 4. You have to increment two counters at 17998h and 179A1h (dont know why) 5. You have to edit the strings "VBOX" "DSDT" and "VBOX" "XDST" at a few places. Then there the point is coming, where i don' know what else to do. I figured out, that i have to use the PE Explorer to increase the "code" area, which ends normally at 92852h. Now it has to end at 928C3h. But i don't know how to fix the several checksums. All i can produce is a not working dll. Greets Obelix
Here are the details about patching, better late than never I use version 3.1.0 for the description, because i saved some information when analyzing back then and don't have the time to do it again These are the differences (i used tiny hexer to compare, jump between the differences with F7 and F8): Length of the relocation segment increased by 4 (only needed, when no unused entry for base of added code exists). Near this you find the length of the code segment, which wasn't increased by the size of the added code. This works, but prevents PE Explorer from diassembling the new code. Better change it, too (see version 3.1.4 differences where to change). String "VBOX" changed String "RSDT" changed String "VBOX" changed String "XSDT" changed Counter changed (add 1) Counter changed (add 1) Call to added code New Code added (REPLACE unsused space, align it: fill (replacing) last used original line with "CC"s), press F8 a few times "VBOX " changed SLIC added (REPLACE unsused space), press F8 a few times Length of relocations for base 00092000 increased by 4 This is the next base for relocations: 00093000. Before this 4 bytes are INSERTED: one relocation pointing to the added code, where the address of the SLIC is referenced, and one unused entry 0000). Now there are a lot of differences, because of the inserted bytes. At the end of all these differences DELETE 4 unused bytes. That's all Here is a little bit of information about what is done and where: The relevant source code can be found in DevACPI.cpp of the Open Source Edition. This is the funtion, where everything is done: Code: /** * Create the ACPI tables. */ static int acpiPlantTables(ACPIState *s) { int rc; RTGCPHYS32 rsdt_addr, xsdt_addr, fadt_acpi1_addr, fadt_acpi2_addr, facs_addr, dsdt_addr, last_addr, apic_addr = 0; uint32_t addend = 0; RTGCPHYS32 rsdt_addrs[4]; RTGCPHYS32 xsdt_addrs[4]; uint32_t cAddr; size_t rsdt_tbl_len = sizeof(ACPITBLHEADER); size_t xsdt_tbl_len = sizeof(ACPITBLHEADER); cAddr = 1; /* FADT */ if (s->u8UseIOApic) cAddr++; /* MADT */ Here you see the counter "cAddr", which is either 1 or 2. Because we add the SLIC, we change this to 2 and 3. Search for "558BEC83EC4C8A86" (was unique in version 3.1.4, too) to get to the right place: Code: Assembler: 10017B6B CCCCCCCCCC Align8 10017B70 SUB_L10017B70: 10017B70 55 pushebp 10017B71 8BEC movebp,esp 10017B73 83EC4C subesp,0000004Ch 10017B76 8A8689120000 moval,[esi+00001289h] 10017B7C 84C0 testal,al 10017B7E C745EC00000000 movdword ptr [ebp-14h],00000000h 10017B85 C745F002000000 movdword ptr [ebp-10h],00000002h// Changed here 10017B8C 7407 jz L10017B95 10017B8E C745F003000000 movdword ptr [ebp-10h],00000003h// and here Where to add the call to the new code? Here, in the middle of "(last_addr > 0x10000)": Code: Source code: if (last_addr > 0x10000) return PDMDEV_SET_ERROR(s->pDevIns, VERR_TOO_MUCH_DATA, N_("Error: ACPI tables > 64KB")); Code: Assembler: 10017D68 8B55F8 movedx,[ebp-08h]// if (last_addr > 0x10000) 10017D6B 8D441A0F leaeax,[edx+ebx+0Fh] 10017D6F 83E0F0 andeax,FFFFFFF0h 10017D72 E879AF0700 callSUB_L10092CF0// already patched Call of added code, was compare previously 10017D77 7630 jbeL10017DA9 10017D79 8B8EAC120000 movecx,[esi+000012ACh] 10017D7F 68E06E0910 pushSSZ10096EE0_Error__ACPI_tables___64KB 10017D84 68A4370910 pushL100937A4 10017D89 68806F0910 pushSSZ10096F80_acpiPlantTables 10017D8E 6880070000 push00000780h 10017D93 68D46D0910 pushSSZ10096DD4_E__tinderbox_win_rel_src_VBox_De 10017D98 6AD6 pushFFFFFFD6h 10017D9A 51 pushecx 10017D9B E8209CFEFF callSUB_L100019C0 10017DA0 83C41C addesp,0000001Ch 10017DA3 5B popebx 10017DA4 5F popedi 10017DA5 8BE5 movesp,ebp 10017DA7 5D popebp 10017DA8 C3 retn Adding the new code: The code could be used without changing the one from version 3.1.0. BUT this may change with a new version, therefore i add the assembler listing with a few comments (Code from patched 3.1.0 VBoxDD.dll): Code: 10092CE2 CCCCCCCCCCCCCCCCCCCC+ Align16 10092CF0 SUB_L10092CF0: 10092CF0 60 pushad 10092CF1 BA76010000 movedx,00000176h// SLIC length 10092CF6 52 pushedx 10092CF7 83C20F addedx,0000000Fh// Align 16 10092CFA 83E2F0 andedx,FFFFFFF0h// Align 16 10092CFD 8B45FC moveax,[ebp-04h]// "last_addr" without SLIC 10092D00 0155FC add[ebp-04h],edx// "last_addr" with SLIC included 10092D03 8B9E80020000 movebx,[esi+00000280h]// Variable "u64RamSize" 10092D09 81EB00000100 subebx,00010000h 10092D0F 03D8 addebx,eax// Loading adress for SLIC 10092D11 8B86AC120000 moveax,[esi+000012ACh]// Import table? 10092D17 8B4818 movecx,[eax+18h]// one DLL in import table? 10092D1A 68804E1910 pushL10194E80// Source SLIC adress (10194E80, already relocated), Relocatable -> add offset D1B within base 92000 10092D1F 6A00 push00000000h 10092D21 53 pushebx 10092D22 50 pusheax 10092D23 FF91F4000000 call[ecx+000000F4h]// Function "acpiSetupDSDT" VBoxVMM (copy SLIC) 10092D29 83C414 addesp,00000014h// Remove stack data (5 x 32 bit) 10092D2C 8A8E89120000 movcl,[esi+00001289h]// Variable "u8UseIOApic" 10092D32 33C0 xoreax,eax 10092D34 84C9 testcl,cl 10092D36 7401 jz L10092D39 10092D38 40 inceax 10092D39 L10092D39: 10092D39 40 inceax 10092D3A 895C85C4 mov[ebp+eax*4-3Ch],ebx// Invalidation of SEH-Pointer of triggered code: VBoxVMM timer 10092D3E 895C85B4 mov[ebp+eax*4-4Ch],ebx// Invalidation of SEH-Pointer 10092D42 61 popad 10092D43 8B5DFC movebx,[ebp-04h]// repeat original code, which was overwritten by call to the added code 10092D46 8D441A0F leaeax,[edx+ebx+0Fh] 10092D4A 83E0F0 andeax,FFFFFFF0h 10092D4D 3D00000100 cmpeax,00010000h 10092D52 C3 retn The used function to add the SLIC ist this one: Code: Source code: Log(("RSDP 0x%08X\n", find_rsdp_space())); addend = s->cbRamLow - 0x10000; Log(("RSDT 0x%08X XSDT 0x%08X\n", rsdt_addr + addend, xsdt_addr + addend)); Log(("FACS 0x%08X FADT (1.0) 0x%08X, FADT (2+) 0x%08X\n", facs_addr + addend, fadt_acpi1_addr + addend, fadt_acpi2_addr + addend)); Log(("DSDT 0x%08X\n", dsdt_addr + addend)); acpiSetupRSDP((ACPITBLRSDP*)s->au8RSDPPage, rsdt_addr + addend, xsdt_addr + addend); -> acpiSetupDSDT(s, dsdt_addr + addend, pDsdtCode, uDsdtSize); acpiCleanupDsdt(s->pDevIns, pDsdtCode); acpiSetupFACS(s, facs_addr + addend); acpiSetupFADT(s, fadt_acpi1_addr + addend, fadt_acpi2_addr + addend, facs_addr + addend, dsdt_addr + addend); rsdt_addrs[0] = fadt_acpi1_addr + addend; xsdt_addrs[0] = fadt_acpi2_addr + addend; Invalidating the exception handler, VBoxVMM timer function: i didn't analyze, why this was done, but i used olly debugger to see, wether the same offsets applied in version 3.1.4 (they did): Stack in olly debugger after call of "acpiPlantTables", but before any execution: Code: 034EFD6C 06F47F20 RETURN to VBoxDD.06F47F20 from VBoxDD.06F47B70 034EFD70 0728BB10 034EFD74 00000000 034EFD78 /034EFDA4 034EFD7C |10036D1F RETURN to VBoxVMM.10036D1F 034EFD80 |0728BB10 034EFD84 |009AB000 034EFD88 |00000007 034EFD8C |00990000 034EFD90 |1004BBDC RETURN to VBoxVMM.1004BBDC from VBoxVMM.1000D9A0 034EFD94 |00990000 034EFD98 |00000001 034EFD9C |00000000 034EFDA0 |00000001 034EFDA4 ]034EFDCC 034EFDA8 |100059FC RETURN to VBoxVMM.100059FC from VBoxVMM.PDMR3Reset 034EFDAC |00990000 034EFDB0 |00990000 034EFDB4 |009AB000 034EFDB8 |00990000 034EFDBC |00990000 034EFDC0 |00990000 034EFDC4 |00000457 034EFDC8 |009AB000 034EFDCC ]034EFE0C 034EFDD0 |100273B5 RETURN to VBoxVMM.100273B5 Stack in olly debugger after some executions: Code: 034EFD1C /034EFD2C 034EFD20 |100843CE RETURN to VBoxVMM.100843CE from VBoxVMM.10083E40 034EFD24 |00990000 034EFD28 |000003E8 034EFD2C ]034EFD68 034EFD30 |06F46F1B RETURN to VBoxDD.06F46F1B from VBoxVMM.TMTimerSet 034EFD34 |00000009 034EFD38 |82DE9E1C 034EFD3C |00000177 034EFD40 |0728D2D0 034EFD44 |FFFFFFFF 034EFD48 |00000000 034EFD4C |3B9ACA00 034EFD50 |00369E99 034EFD54 |0728D2D0 034EFD58 |00000000 034EFD5C |00000000 034EFD60 |00990000 034EFD64 |00000000 034EFD68 ]034EFD78 034EFD6C |06F47F20 RETURN to VBoxDD.06F47F20 from VBoxDD.06F47B70// first line from above stack listing The exception handlers of the two new stack frames within VBoxVMM have to be invalidated. Generally: when adding the SLIC loading code to a new version of Virtual Box, make sure the offsets are still the same within the new version. Use the original code to see which ones have to be used. If they have changed, adapt them to the new ones. This includes the function call "acpiSetupDSDT" (import table, dll), the variables and the SEH-pointer offsets. Relocation Table: every entry is 16 bits length, 4 bits type (3, or 0 for unused) and 12 bits offset within the base. The base this time (3.1.0 and 3.1.4) was 92000, but it may change in newer versions. If there is no unused entry within the desired base, you have to add 2 entries (4 bytes) and mark one as unused (00 00). I hope this helps and you are able to patch the new version 3.1.6
well with the release of 3.2.0 the vboxdd.dll from 3.1.x no longer works! hopefully someone can build a new one.