Partager via


Symboles de mappage lorsque le PEB est mis hors page

Pour charger des symboles, le débogueur examine la liste des modules chargés par le système d’exploitation. Le pointeur vers la liste des modules en mode utilisateur est l’un des éléments stockés dans le bloc d’environnement de processus (PEB).

Pour récupérer de la mémoire, le Gestionnaire de mémoire peut pager des données en mode utilisateur afin de faire de l’espace pour d’autres composants de processus ou de mode noyau. Les données en mode utilisateur qui sont paginées peuvent inclure la structure de données PEB. Sans cette structure de données, le débogueur ne peut pas déterminer pour quelles images charger des symboles.

Note Cela affecte uniquement les fichiers de symboles pour les modules en mode utilisateur. Les symboles et modules en mode noyau ne sont pas affectés, car ils sont suivis dans une autre liste.

Supposons qu’un module en mode utilisateur soit mappé au processus actuel et que vous souhaitez corriger les symboles pour celui-ci. Recherchez n’importe quelle adresse dans la plage d’adresses virtuelles du module. Par exemple, supposons qu’un module soit mappé dans une plage d’adresses virtuelle qui contient l’adresse 7f78e9e000F. Entrez la commande suivante.

3: kd> !vad 7f78e9e000F 1

La sortie de commande affiche des informations sur le descripteur d’adresse virtuelle (VAD) du module. La sortie de commande inclut également une chaîne de commande Recharger que vous pouvez utiliser pour charger les symboles du module. La chaîne de commande Recharger inclut l’adresse de départ (000007f7'8e9e00000) et la taille (32000) du module bloc-notes.

VAD @ fffffa80056fb960
...
Reload command: .reload notepad.exe=000007f7`8e9e0000,32000

Pour charger les symboles, entrez la commande qui a été donnée dans la chaîne de commande Recharger.

.reload notepad.exe=000007f7`8e9e0000,32000

Voici un autre exemple qui utilise une technique légèrement différente. L’exemple montre comment utiliser l’extension !vad pour mapper des symboles lorsque le PEB est paginé. L’idée de base est de trouver l’adresse de départ et la taille de la DLL appropriée afin que vous puissiez ensuite utiliser la commande .reload pour charger les symboles nécessaires. Supposons que l’adresse du processus actuel soit 0xE0000126'01BA0AF0 et que vous souhaitez corriger les symboles correspondants. Tout d’abord, utilisez la commande !process pour obtenir l’adresse racine du descripteur d’adresse virtuelle (VAD) :

kd> !process e000012601ba0af0 1
PROCESS e000012601ba0af0
    SessionId: 2  Cid: 0b50    Peb: 6fbfffde000  ParentCid: 0efc
    DirBase: 079e8461  ObjectTable: e000000600fbceb0  HandleCount: 360.
    Image: explorer.exe
    VadRoot e000012601a35e70 Vads 201 Clone 0 Private 917. Modified 2198. Locked 0.
...

Ensuite, utilisez l’extension !vad pour répertorier l’arborescence VAD associée au processus. Les VAD étiquetés « EXECUTE_WRITECOPY » appartiennent à des modules de code.

kd> !vad e000012601a35e70
VAD     level      start      end    commit
...
e0000126019f9790 ( 6)      3fff0    3fff7        -1 Private      READONLY
e000012601be1080 ( 7)   37d9bd30 37d9bd3e         2 Mapped  Exe  EXECUTE_WRITECOPY  <-- these are DLLs
e000012600acd970 ( 5)   37d9bec0 37d9bece         2 Mapped  Exe  EXECUTE_WRITECOPY
e000012601a5cba0 ( 7)   37d9c910 37d9c924         2 Mapped  Exe  EXECUTE_WRITECOPY
...

Ensuite, utilisez à nouveau l’extension !vad pour rechercher l’adresse de départ et la taille de la mémoire paginée qui contient la DLL d’intérêt. Cela confirme que vous avez trouvé la DLL appropriée :

kd> !vad e000012601be1080 1

VAD @ e000012601be1080
  Start VPN:      37d9bd30  End VPN: 37d9bd3e  Control Area:  e00001260197b8d0
  First ProtoPte: e0000006013e00a0  Last PTE fffffffffffffffc  Commit Charge         2 (2.)
  Secured.Flink          0  Blink           0  Banked/Extend:        0
  File Offset   0
   ImageMap ViewShare EXECUTE_WRITECOPY

...
        File: \Windows\System32\ExplorerFrame.dll

Le champ « Démarrer le VPN » (dans ce cas, 0x37D9BD30) indique le numéro de la page virtuelle de démarrage. Cela doit être converti en adresse réelle, en la multipliant par la taille de page. Vous pouvez utiliser le ? (Évaluer l’expression) commande pour multiplier cette valeur par 0x2000, qui correspond à la taille de page de l’ordinateur Itanium d’où provient l’exemple.

kd> ? 37d9bd3e*2000 
Evaluate expression: 7676040298496 = 000006fb`37a7c000

Ensuite, la taille de la plage peut être convertie en octets :

kd> ? 37d9bd3e-37d9bd30+1 <--   computes the number of pages
Evaluate expression: 15 = 00000000`0000000f
kd> ? f*2000
Evaluate expression: 122880 = 00000000`0001e000        

Par conséquent, ExplorerFrame.dll commence à l’adresse 0x000006Fb'37A7C000 et a une taille de 0x1E000 octets. Vous pouvez charger ses symboles avec :

kd> .reload /f ExplorerFrame.dll=6fb`37a7c000,1e000