Jump to content

[WIP] Windows Vista Extended Kernel


win32

Recommended Posts

4 hours ago, win32 said:

I believe that x64 binaries have been available for Office since 2010. If he were trying to run the x86 version, then it would have been asking for a lot more than SetWaitableTimerEx in kernel32.

If @TECHGEEK's WINWORD.EXE is x86, then it would be a good idea to see if SetWaitableTimerEx from KernelXE R2 is enough to make Word happy. It's not really a good implementation, but it's probably good enough for some programs.

Here is an x64 implementation of SetWaitableTimerEx that is similar to the one in KernelXE R2:

mov     [rsp+pfnCompletionRoutine], r9
mov     [rsp+lPeriod], r8d
mov     [rsp+lpDueTime], rdx
mov     [rsp+hTimer], rcx
sub     rsp, 38h
mov     [rsp+38h+fResume], 1 ; fResume
mov     rax, [rsp+38h+lpArgToCompletionRoutine]
mov     [rsp+38h+var_18], rax ; lpArgToCompletionRoutine
mov     r9, [rsp+38h+pfnCompletionRoutine] ; pfnCompletionRoutine
mov     r8d, [rsp+38h+lPeriod] ; lPeriod
mov     rdx, [rsp+38h+lpDueTime] ; lpDueTime
mov     rcx, [rsp+38h+hTimer] ; hTimer
call    SetWaitableTimer
add     rsp, 38h
retn

I attached the hex code for this function to save time just in case @win32 considers adding it to kernel32.

SetWaitableTimerEx.hex

Edited by Ximonite
Added x64 version of SetWaitableTimerEx
Link to comment
Share on other sites


5 hours ago, Ximonite said:

I attached the hex code for this function to save time just in case @win32 considers adding it to kernel32.

Yes, I was planning on adding it in the next update beforehand, as it's the only outstanding function for Office 2019 x64 setup. Then there's RtlGetVersion that can spoof NT 10.0 (installers for recent MS software generally don't like running in compatibility mode/Application Verifier), and we should be set.

x86 things are probably harder than that because of some K32* functions not working as well as they should. Your K32GetPerformanceInfo implementation seems similar to mine (and Windows 7's, which is a rearranged version of Vista's psapi.GetPerformanceInfo), so once we get the opportunity to test it, I wonder if it will work or it will fail in the same places as mine did (calls to NtQueryInformationProcess and similar functions). Then it will prove that those ntoskrnl functions are the problem on everything below Windows 7.

Link to comment
Share on other sites

1 hour ago, win32 said:

Yes, I was planning on adding it in the next update beforehand, as it's the only outstanding function for Office 2019 x64 setup. Then there's RtlGetVersion that can spoof NT 10.0 (installers for recent MS software generally don't like running in compatibility mode/Application Verifier), and we should be set.

x86 things are probably harder than that because of some K32* functions not working as well as they should. Your K32GetPerformanceInfo implementation seems similar to mine (and Windows 7's, which is a rearranged version of Vista's psapi.GetPerformanceInfo), so once we get the opportunity to test it, I wonder if it will work or it will fail in the same places as mine did (calls to NtQueryInformationProcess and similar functions). Then it will prove that those ntoskrnl functions are the problem on everything below Windows 7.

As long as the Office 2019 setup doesn't care about fResume always being 1, then the code I provided should be good enough.

I don't remember where the code for my implementation of K32GetPeformanceInfo came from, but if it doesn't work, I'm planning to try out GetPeformanceInfo from One Core API because it works on XP. It does have a fairly big function chunk which will be annoying to reattach to the rest of the function. The K32 functions in KernelXE R2 came from many different places, including your x86 kernel32.dll, so there's a lot of potential for something to be wrong with my implementations. I also know for sure that there are many missing security patches in my implementations of basically everything. I get to look forward to going through 8 years of security patches and going through every change to every function and figuring out what goes where in the Windows 2000 files. That's going to be one hell of an experience for me and one huge benefit to people using Windows 2000.

Are you planning to upgrade your extended kernel files to the latest ones from the Server 2008 ESU updates? That would be very helpful, but would become obsolete quickly. Feature support will stay the same though, since Server 2008 is only getting security updates now.

Kinda unrelated, but do you know of any tools for adding relocations other than WildBill's PE Tool? I don't like how I have to wait about 10 seconds every time I add a relocation. I have heard that there is some tool out there that automatically finds and adds all the needed relocations to .reloc, but I don't know if it actually exists or not.

Link to comment
Share on other sites

2 hours ago, Ximonite said:

I'm planning to try out GetPeformanceInfo from One Core API because it works on XP. It does have a fairly big function chunk which will be annoying to reattach to the rest of the function.

That's byte-for-byte equivalent to Vista's psapi.GetPerformanceInfo. I tried making K32GetPerformanceInfo (and some other K32 functions) redirect to their PSAPI_VERSION_1 equivalents. The only difference was Advanced Chrome 84 crashing silently instead of the dispatching of a crash dialog. 8.1's (K32)GetPerformanceInfo is a little different (and is self-contained), but I remember that no matter what implementation it was, the problem was NtQuerySystemInformation/NtQueryInformationProcess/etc. Those may return more subparameters in 7 x86 than in Vista x86, which may be where the problem lies.

2 hours ago, Ximonite said:

Are you planning to upgrade your extended kernel files to the latest ones from the Server 2008 ESU updates? That would be very helpful, but would become obsolete quickly. Feature support will stay the same though, since Server 2008 is only getting security updates now.

No. I chose 2017 as it predates a major performance drop in Windows binaries and Spectre/Meltdown mitigations. It would also be a lot of work refactoring everything. I thought about putting the new functions in wrappers linking back to the extant kernel32, and maybe trying some stuff with knowndlls to somehow make the redirection seamless like it is for custom ntoskrnls with different names, but shared data structures and subroutines would be a problem.

And while I'm at it, there is going to be an installer, using a batch script. Admin privileges required. It renames the files in use, copies the new ones, and requires a reboot. I am also going to self-sign the files to satisfy the VirtualBox hardening requirements (you may have to do the same thing if you want to run 4.2.xx/4.3xx+ on Windows 2000).

Edited by win32
Link to comment
Share on other sites

11 hours ago, win32 said:

That's byte-for-byte equivalent to Vista's psapi.GetPerformanceInfo. I tried making K32GetPerformanceInfo (and some other K32 functions) redirect to their PSAPI_VERSION_1 equivalents. The only difference was Advanced Chrome 84 crashing silently instead of the dispatching of a crash dialog. 8.1's (K32)GetPerformanceInfo is a little different (and is self-contained), but I remember that no matter what implementation it was, the problem was NtQuerySystemInformation/NtQueryInformationProcess/etc. Those may return more subparameters in 7 x86 than in Vista x86, which may be where the problem lies.

Very weird that a Vista function would work on XP but not Vista. :unsure:

In NtQuerySystemInformation, there are jumptables that look very similar C++ switch statements (they probably are C++ switch statements in the source code).

I noticed that in the Vista version, the first jumptable has 57 cases and the second one has 49 cases, but the 7 version has 63 cases in the first jumptable and 61 cases in the second jumptable. These may be the subparameters you are talking about.

The hex rays decompiler displays names of what I assume are the subparameters you are talking about when decompiling your implementation of K32GetPeformanceInfo. This may be helpful.

if ( InformationLength >= 0x38 )
{
  v4 = NtQuerySystemInformation(SystemBasicInformation, &SystemInformation, 0x2Cu, 0);
  if ( v4 >= 0
    && (v4 = NtQuerySystemInformation(SystemPerformanceInformation, &v14, 0x148u, 0), v4 >= 0)
    && (v4 = NtQuerySystemInformation(SystemFileCacheInformation, &v21, 0x24u, 0), v4 >= 0) )
Status = NtQuerySystemInformation(SystemProcessInformation, hMem, InformationLengtha, &ResultLength);

Now we just need to figure out which cases in the jumptables correspond with each subparameter, if that's even what the jumptables are for.

11 hours ago, win32 said:

No. I chose 2017 as it predates a major performance drop in Windows binaries and Spectre/Meltdown mitigations. It would also be a lot of work refactoring everything. I thought about putting the new functions in wrappers linking back to the extant kernel32, and maybe trying some stuff with knowndlls to somehow make the redirection seamless like it is for custom ntoskrnls with different names, but shared data structures and subroutines would be a problem.

Making wrappers for the new functions is a really good idea, especially now that Windows Update works on Vista again. I really hope that someone figures out a way to get ESU updates through Windows Update.

The reason why I didn't try making wrappers for KernelXE R2 is because I don't have to worry about Microsoft updating basically any of the files. usp10.dll and gdiplus.dll are still updated by Microsoft, but I'm pretty sure those don't have any reason to be modified.

Link to comment
Share on other sites

2 hours ago, Ximonite said:

Very weird that a Vista function would work on XP but not Vista. :unsure:

psapi.GetPerformanceInfo works when a program calls GetPerformanceInfo, obviously. Problems only arise when K32GetPerformanceInfo is brought into the equation. And I also neglected to mention that NtQueryInformationProcess also causes crashes in shell32.SetCurrentProcessExplicitAppUserModelID (from Windows 7) on Vista x86, in addition to K32GetProcessMemoryInfo so I don't think that our K32* implementations are bad.

2 hours ago, Ximonite said:

The hex rays decompiler displays names of what I assume are the subparameters you are talking about when decompiling your implementation of K32GetPeformanceInfo. This may be helpful.

Those subparameters don't seem to further the understanding of the situation, considering that they have been around since NT 3.x. But I'm not sure about v14 and v21 for &SystemInformation. Perhaps it should be compared with the original GetPerformanceInfo from Vista. Then for NtQueryInformationProcess, we should compare K32GetProcessMemoryInfo, psapi.GetProcessMemoryInfo and SetCurrentProcessExplicitAppUserModelID. If only my development environment wasn't so fragmented to have equal access to tools at all locations... :dubbio:

2 hours ago, Ximonite said:

usp10.dll and gdiplus.dll are still updated by Microsoft, but I'm pretty sure those don't have any reason to be modified.

A newer version of gdiplus, as a higher-level DLL, can easily be dropped in. That is true for the Windows 7 versions on Vista x64, which will be needed for the latest versions of paint.net.

Edited by win32
Link to comment
Share on other sites

2 hours ago, win32 said:

psapi.GetPerformanceInfo works when a program calls GetPerformanceInfo, obviously. Problems only arise when K32GetPerformanceInfo is brought into the equation. And I also neglected to mention that NtQueryInformationProcess also causes crashes in shell32.SetCurrentProcessExplicitAppUserModelID (from Windows 7) on Vista x86, in addition to K32GetProcessMemoryInfo so I don't think that our K32* implementations are bad.

I feel like our K32* implementations are pretty good, since the decompiled code for both of ours are very similar to the Windows 7 functions.

I wonder how NtQueryInformationProcess could be causing issues with shell32.SetCurrentProcessExplicitAppUserModelID, especially since the implementations I have seen don't even call NtQueryInformationProcess. Here is the one non-stub I have seen:

mov     eax, lpString
test    eax, eax
jnz     short loc1
push    [esp+AppID]     ; lpString
call    ds:lstrlenW
inc     eax
add     eax, eax
push    eax
call    ds:CoTaskMemAlloc
mov     lpString, eax
push    [esp+AppID]     ; lpString2
push    eax             ; lpString1
call    ds:lstrcpyW
xor     eax, eax
retn    4
loc1:
mov     eax, 80004005h
retn    4

lstrlenW and lstrcpyW from kernel32. CoTaskMemAlloc from ole32. lpString is a dword that is 0 in the file and only accessed by shell32.SetCurrentProcessExplicitAppUserModelID and shell32.GetCurrentProcessExplicitAppUserModelID

SetCurrentProcessExplicitAppUserModelID.hex

Link to comment
Share on other sites

13 minutes ago, Ximonite said:

I wonder how NtQueryInformationProcess could be causing issues with shell32.SetCurrentProcessExplicitAppUserModelID, especially since the implementations I have seen don't even call NtQueryInformationProcess. Here is the one non-stub I have seen:

woah, that is simple compared to this one from 7 SP1 which does call NtQueryInformationProcess:

.text:7390C954 SetCurrentProcessExplicitAppUserModelID proc near
.text:7390C954                                         ; DATA XREF: .text:off_738B57E0↑o
.text:7390C954
.text:7390C954 var_20          = byte ptr -20h
.text:7390C954 var_1C          = dword ptr -1Ch
.text:7390C954 var_8           = dword ptr -8
.text:7390C954 var_4           = dword ptr -4
.text:7390C954 arg_0           = dword ptr  8
.text:7390C954
.text:7390C954 ; FUNCTION CHUNK AT .text:739B746A SIZE 0000002A BYTES
.text:7390C954
.text:7390C954                 mov     edi, edi
.text:7390C956                 push    ebp
.text:7390C957                 mov     ebp, esp
.text:7390C959                 sub     esp, 20h
.text:7390C95C                 mov     eax, ___security_cookie
.text:7390C961                 xor     eax, ebp
.text:7390C963                 mov     [ebp+var_4], eax
.text:7390C966                 mov     eax, [ebp+arg_0]
.text:7390C969                 mov     [ebp+var_8], eax
.text:7390C96C                 lea     edx, [eax+2]
.text:7390C96F
.text:7390C96F loc_7390C96F:                           ; CODE XREF: SetCurrentProcessExplicitAppUserModelID+23↓j
.text:7390C96F                 mov     cx, [eax]
.text:7390C972                 inc     eax
.text:7390C973                 inc     eax
.text:7390C974                 test    cx, cx
.text:7390C977                 jnz     short loc_7390C96F
.text:7390C979                 sub     eax, edx
.text:7390C97B                 sar     eax, 1
.text:7390C97D                 push    esi
.text:7390C97E                 cmp     eax, 80h
.text:7390C983                 sbb     esi, esi
.text:7390C985                 and     esi, 7FF8FFA9h
.text:7390C98B                 add     esi, 80070057h
.text:7390C991                 js      loc_7390CA1E
.text:7390C997                 push    0
.text:7390C999                 push    18h
.text:7390C99B                 lea     eax, [ebp+var_20]
.text:7390C99E                 push    eax
.text:7390C99F                 push    0
.text:7390C9A1                 call    ds:GetCurrentProcess
.text:7390C9A7                 push    eax
.text:7390C9A8                 call    ds:NtQueryInformationProcess

[...]

I do remember trying a different implementation from BWC, but got a BEX. There is also the option of getting the subfunctions from kernel32 functions (like NtQueryInformationProcess.ProcessBasicInformation can be replaced by calls to CheckRemoteDebuggerPresent and GetProcessId).

If a solution can be found for this problem, many compatibility problems from NT 5.0 to 6.0 x86 would be eliminated.

Link to comment
Share on other sites

On 10/24/2020 at 3:20 PM, win32 said:

It would be very difficult to duplicate the work I did for the 2017-based files for those. But you may want to try local DLL redirection...

Hello , sadly it didn't work with Opera , I did all aforementioned steps , rebooted , yet it still wants TryAcquireSRWLockExclusive.

I even tried older versions , like 60 . I'm using extended files dated July 2020, from the known youtube video.

 

Link to comment
Share on other sites

2 hours ago, Dixel said:

Hello , sadly it didn't work with Opera , I did all aforementioned steps , rebooted , yet it still wants TryAcquireSRWLockExclusive.

I even tried older versions , like 60 . I'm using extended files dated July 2020, from the known youtube video.

Then you are probably using a 32 bit version of Opera. The latest 64 bit version still needs one or two more functions anyway.

Link to comment
Share on other sites

Just now, win32 said:

Then you are probably using a 32 bit version of Opera. The latest 64 bit version still needs one or two more functions anyway.

Thanks for the quick reply , both versions (32 and 64bit) won't launch . They are just giving different errors , x64 bit shows :  SHAssocEnumHandlersForProtocolByApplication not found in shell32.dll

And no , I'm not trying the latest versions . It's Opera 60 and earlier.

Edit : maybe the patched files are old , but I don't know where to find their newer versions...

Edited by Dixel
Link to comment
Share on other sites

4 minutes ago, Dixel said:

SHAssocEnumHandlersForProtocolByApplication not found in shell32.dll

Yes, that is a problem that affects even the latest versions of Opera x64. I haven't added that function yet but do plan to do it in the release after next.

Link to comment
Share on other sites

53 minutes ago, win32 said:

Yes, that is a problem that affects even the latest versions of Opera x64. I haven't added that function yet but do plan to do it in the release after next.

isnt SHAssocEnumHandlersForProtocolByApplication also required for chromium edge aswell?

Link to comment
Share on other sites

11 minutes ago, burd said:

isnt SHAssocEnumHandlersForProtocolByApplication also required for chromium edge aswell?

I don't remember, but Edge also needs secur32 (perhaps a complete replacement of the file along with other crypto stuff since it's high-level enough?) and ntdll functions.

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...