Home WinDbg Preview - a dirty fix for "Levels not implemented for this platform"
Post
Cancel

WinDbg Preview - a dirty fix for "Levels not implemented for this platform"

The issue

Imagine being deep into a kernel debugging session and suddenly your debugger stops working as expected.

(Levels not implemented for this platform)

(This has been going on for years at this point and it doesn’t look like there’s active interest in fixing or investigating the bug, yet.)

Still, it continues to be a crippling bug that affects us at the worst possible times.

Rebooting to roll the dice in hopes this will temporarily fix the issue might be out of the question since debugging without symbols is already quite involved, and scrapping progress in for convenience’s sake feels like a massive waste of time, so let’s try to figure out what causes this to happen by looking at the symptoms.

KdExts.dll

Extensions! !pte is what’s called an extension in WinDbg terms, that is, it’s not core functionality since it only applies to kernel debugging sessions. It is therefore implemented in the Kernel Debugger Extensions DLL (KdExts.dll) found in the install directory of WinDbg - which is likely somewhere in C:\Program Files\WindowsApps, for my particular version it is found at
C:\Program Files\WindowsApps\Microsoft.WinDbg_1.2210.3001.0_x64__8wekyb3d8bbwe\amd64\winxp\kdexts.dll

I’ll save you the trouble of finding where exactly the “Levels not implemented for this platform” message is referenced (you can do this an exercise if you’d like), and show you what the code responsible looks like once decompliled:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
  ...
  switch ( g_TargetMachine )                     // debuggee machine's arch
  {
    case IMAGE_FILE_MACHINE_I386:
      goto I386;
    case IMAGE_FILE_MACHINE_ARM:
    case IMAGE_FILE_MACHINE_THUMB:
    case IMAGE_FILE_MACHINE_ARMNT:
      v10 = 10;
  I386:
      v9 = 2;
      if ( !PaeEnabled )
        v10 = 10;
      break;
    case IMAGE_FILE_MACHINE_AMD64:             // we're obviously debugging an x64 machine
      v9 = DbgPagingLevels;
      if ( (unsigned int)DbgPagingLevels > 5 ) // Paging levels above 5 aren't implemented yet
      {
        msg = "Levels not implemented for this platform\n";
        goto FAIL;
      }
      break;
    ...
  FAIL:
      ExtensionApis.lpOutputRoutine(msg);
      return -1;
  }
  ...

If you’re not familiar with paging, this odsev article has some insight into why our bug is so absurd.

WinDbg-Inception

Here comes the dirty fix part.

We have :

  • symbols for kdexts.dll;
  • a debugger (yes, we’ll use WinDbg to patch WinDbg);
  • a good sense of humor

thanos

The fix

Steps:

  • open a second instance of WinDbg and attach to the faulty instance;
  • issue the .reload /f command to force symbol loading;
  • locate the g_TargetMachine global variable and confirm it’s still IMAGE_FILE_MACHINE_AMD64 (0x8664)

image

  • great, let’s look at DbgPagingLevels

image

That makes no sense.

Let’s edit the memory to reflect the correct value (which as of Feb 2023 should be either 4 or 5 depending on your CPU/Windows Edition combo). I’ll edit it to 4, because of my CPU is quite an old one and I’m not using Windows Server edition. (This is bound to be way more variable in the future, but by then, hopefully you won’t need this guide anymore).

image

  • hit g or Go button and make sure your Kd debugger instance is stable
  • detach from from it and close the second WinDbg instance
  • now try !pte again

image

And that’s it, you can keep on hunting bugs.

I hope this was useful.


Note:

This is not a proper fix, and this article skips the root cause analysis of this behavior. It is intended to be a quick way of dealing with the issue when it presents itself.

Additional analysis may or may not be posted here as an update, but for now I’m only interested in continuing the work I was interrupted from.

This post is licensed under CC BY 4.0 by the author.
Trending Tags