首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >如何将虚拟地址(WinDbg)转换成物理地址?

如何将虚拟地址(WinDbg)转换成物理地址?
EN

Stack Overflow用户
提问于 2019-10-04 16:38:02
回答 1查看 1.4K关注 0票数 2

好像我不明白什么。

我正试图在VirtualBox下将VA翻译成Windows 10上的PA (VirtualBox)。我用Microsoft手册来做这个。我设置了一个本地内核调试器(bcedit),并将CFF探索者作为一个测试应用程序启动。然后我启动了WinDbg,连接到内核并获得活动进程:

代码语言:javascript
运行
复制
!process 0 0

找到我的测试应用程序:

代码语言:javascript
运行
复制
    PROCESS a6bd7900  SessionId: 1  Cid: 0988    Peb: 7ffd9000  ParentCid: 0840
    DirBase: ba9ac3c0  ObjectTable: acaeedc0  HandleCount: <Data Not Accessible>
    Image: CFF Explorer.exe

那就去找PEB:

代码语言:javascript
运行
复制
.process /p a6bd7900; !peb 7ffd9000

Implicit process is now a6bd7900
PEB at 7ffd9000
    ...
    ImageBaseAddress:         00400000
    ...
    Ldr                       76f99aa0
    Ldr.Initialized:          Yes
    Ldr.InInitializationOrderModuleList: 00881658 . 00887c00
    Ldr.InLoadOrderModuleList:           00881728 . 00887bf0
    Ldr.InMemoryOrderModuleList:         00881730 . 00887bf8
    Base TimeStamp                     Module
    400000 50a8fbd6 Nov 18 18:16:38 2012 C:\Program Files\NTCore\Explorer Suite\CFF Explorer.exe
    76e90000 580ee2c9 Oct 25 07:42:49 2016 C:\WINDOWS\SYSTEM32\ntdll.dll
    74970000 57cf8f7a Sep 07 06:54:34 2016 C:\WINDOWS\system32\KERNEL32.DLL
    ...

我输入了"!r“命令来打印所有寄存器:

代码语言:javascript
运行
复制
cr0 Value: 00720054
cr2 Value: 00720054
cr3 Value: 00720054
cr4 Value: 00720054

cr4 in bin: 00000000,00001010,11111100,10110110,第5位是真,这意味着启用了PAE

然后打开内存窗口并键入400000地址以检查虚拟内存中是否有CFF Explorer.exe的标头。

然后,我试图通过PTE扩展 (通过手册)获得页面帧号:

代码语言:javascript
运行
复制
lkd> !pte 00400000
                    VA 00400000
PDE at C0600010            PTE at C0002000
contains 0000000000000000
contains 0000000000000000
not valid

我没有一个无效的地址。同时,当我试图获得kernel32.dll的PFN时,我得到了有效地址:

代码语言:javascript
运行
复制
lkd> !pte 74970000 
                    VA 74970000
PDE at C0601D20            PTE at C03A4B80
contains 000000000121B867  contains 800000006F1CE005
pfn 121b      ---DA--UWEV  pfn 6f1ce     -------UR-V

然后通过"!dc 6f1ce000“成功地通过物理地址获得报头。

然后,我检查了windbg.exe本身,并注意到有与CFF Explorer.exe相同的基址。我一直认为每个进程都有自己的依赖模块映射到自己的内存,但现在似乎并非如此。

我的问题:

  1. 为什么在翻译0x00400000地址时,我会得到“无效”?
  2. 请用kernel32.dll澄清一下情况,以及我对将模块映射到每个进程的疑虑。

UPDATE 0:我不知道为什么,但是当我将内核调试为本地时,我在所有寄存器中看到了相同的值。我试图远程调试内核,现在我看到了每个寄存器的不同值:

代码语言:javascript
运行
复制
cr0 Value: 80010033
cr2 Value: 909a301c
cr3 Value: 001a8000
cr4 Value: 000406e9

现在,我无法得到kernel32.dll或其他模块的翻译。主要问题已经开始。

EN

回答 1

Stack Overflow用户

发布于 2022-07-06 15:31:00

在设置进程上下文时,!pte可能无法在没有大写/P的情况下工作,因为!pte通过虚拟地址读取页面表条目的内容,从nt!MmPteBase开始(在我的例子中,这是一个内核地址)--记住页面表在内核虚拟内存中,这意味着PTs/PML4 4本身有内核虚拟地址,因此启用用户模式地址旁路不会阻止内核地址仍然在硬件中被翻译。

没有/P,调试器自然将使用逻辑核中当前进程的页表来使用CPU上的硬件转换来访问该虚拟地址的数据,这对于非进程唯一的虚拟地址很好,因为相同的物理页被映射到所有页表中,所以不管核心中当前的表是什么,但是它不会对任何用户虚拟内存起作用,因为所有用户内存都是进程独有的(其中虚拟页映射到对进程唯一的物理页),而且它也不适用于进程特有的任何内核虚拟内存。进程所特有的内核虚拟内存的一个例子是用户地址的页,以及包含页表的内核地址的页表。

为了绕过这一点,使用了/p和/P,调试器访问软件中正确的目录,并在软件中遍历页面表。/p只对所有用户模式地址进行旁路,/P也对所有内核模式地址进行旁路。

代码语言:javascript
运行
复制
lkd> !process 0 0 calc.exe
PROCESS fffffa805d954b10
    SessionId: 1  Cid: 3294    Peb: 7fffffdb000  ParentCid: 10f8
    DirBase: 27a385000  ObjectTable: fffff8a02a766e60  HandleCount:  81.
    Image: calc.exe


lkd> .process /p fffffa805d954b10
Implicit process is now fffffa80`5d954b10
lkd> !pte 0`ffbe0000
                                           VA 00000000ffbe0000
PXE at FFFFF6FB7DBED000    PPE at FFFFF6FB7DA00018    PDE at FFFFF6FB40003FE8    PTE at FFFFF680007FDF00
contains 00C0000263E77867  contains 0000000000000000
pfn 263e77    ---DA--UWEV  not valid

----------------------------------------------------------------------------------------

lkd> .process /P fffffa805d954b10
Implicit process is now fffffa80`5d954b10
lkd> !pte 0`ffbe0000
                                           VA 00000000ffbe0000
PXE at FFFFF6FB7DBED000    PPE at FFFFF6FB7DA00018    PDE at FFFFF6FB40003FE8    PTE at FFFFF680007FDF00
contains 00C000000B023867  contains 00D0000759124867  contains 00E0000792FA5867  contains 80F000004D7DD025
pfn b023      ---DA--UWEV  pfn 759124    ---DA--UWEV  pfn 792fa5    ---DA--UWEV  pfn 4d7dd     ----A--UR-V

!vtop 0 ffbe0000将在不使用/p或/P的情况下工作,因为它从EPROCESS结构中获取脏的PML4物理地址(EPROCESS处于非⁠进程--它可以使用任何页表访问的唯一内核内存),然后它按物理地址映射到正确的页表的PML4物理页中,显示它们的物理地址,并将层次结构中下一个条目的每个物理地址映射到虚拟内存中,以便它能够读取并继续遍历。

!pte fffffa80`5d954b10 ( EPROCESS地址)将在不使用/p或/P的情况下工作,因为EPROCESS物理页面块碰巧映射到位于同一个虚拟地址的所有页表中,因此无论转换是否被调试器绕过,还是在硬件中使用当前处于核心中的任何页表进行转换都无关紧要。

在我看来,您只需要对整个调试会话执行一次/p或/P操作,为了将其重置为.cache nodecodeptes,由于某些原因,在本地调试会话中不能这样做:

代码语言:javascript
运行
复制
lkd> .process /P fffffa805d954b10
Implicit process is now fffffa80`5d954b10
lkd> !pte 10000
                                           VA 0000000000010000
PXE at FFFFF6FB7DBED000    PPE at FFFFF6FB7DA00000    PDE at FFFFF6FB40000000    PTE at FFFFF68000000080
contains 00C000000B023867  contains 01300001F5CA7867  contains 014000030E728867  contains 8D400001A4654867
pfn b023      ---DA--UWEV  pfn 1f5ca7    ---DA--UWEV  pfn 30e728    ---DA--UWEV  pfn 1a4654    ---DA--UW-V

------------------------------------------

lkd> .process fffffa8027653b10
Implicit process is now fffffa80`27653b10
lkd> !pte 10000
                                           VA 0000000000010000
PXE at FFFFF6FB7DBED000    PPE at FFFFF6FB7DA00000    PDE at FFFFF6FB40000000    PTE at FFFFF68000000080
contains 12B0000195039867  contains 036000016A13C867  contains 01400001730BD867  contains FFFFFFFF00000480
pfn 195039    ---DA--UWEV  pfn 16a13c    ---DA--UWEV  pfn 1730bd    ---DA--UWEV  not valid
                                                                                  Proto: VAD
                                                                                  Protect: 4 - ReadWrite

我的意思是说,/p和/P的行为分别与.cache forcedcodeuser.cache forcedecodeptes相同。忽略/p和/P并不会执行.cache nodecodeptes,而是保持原样,因此一旦在一个进程上设置了/p,它将应用于所有进程(尽管msdn说了什么,我认为这是错误的),然后您可以切换到新进程上的/P,然后/P将应用于所有进程。当您启动会话时,当前状态是.cache nodecodeptes,在这种状态下,它依赖于当时实际位于处理器逻辑核心中的页表,对于本地调试来说,该页表将是kd.exe,对于远程调试来说,它将是任何线程闯入调试器的进程。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/58240242

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档