このトピックでは、PoolMon の使用例を次に示します。
例 1: PoolMon 出力の表示と並べ替え
例 2: ディスプレイ ドライバー名
例 3: メモリリークを検出する
例 4: プール のメモリ リークを調べる
例 5: ターミナル サーバー セッションを監視する
例 1: PoolMon 出力の表示と並べ替え
この例では、PoolMon ディスプレイを構成するさまざまな方法について説明します。 既定では、PoolMon はすべてのカーネル メモリ割り当てを英数字順にタグ値で表示します。 表示の並べ替え順序は、コマンド ラインまたは PoolMon の実行中に変更できます。
次のコマンドは、PoolMon を起動します。
poolmon
次のコマンドは、PoolMon を起動し、空き操作の数で表示を並べ替えます。
poolmon /f
poolmon の実行中は、実行時コマンドを使用して表示を変更できます。 たとえば、使用したバイト数で表示を並べ替えるには、 b キーを押します。 割り当てごとにバイト数で並べ替えるには、 m キーを押します。
次のコマンドは、PoolMon を起動し、ノンページ プールからの割り当てのみを表示します。
poolmon /p
PoolMon の実行中、 p キーを押して、ページ プール、非ページ プール、またはその両方からの割り当てを切り替えます。
PoolMon を開始し、特定のタグを使用して割り当てのデータを表示するには、 /i パラメーターを使用します。 次のコマンドは、 AfdB タグ (データ バッファーの afd.sys で使用されるタグ) を使用して割り当てを表示します。
poolmon /iAfdB
特定のタグで割り当てを除外するには、 /x パラメーターを使用します。 次のコマンドは、 AfdB タグを持たないすべての割り当てを表示します。
poolmon /xAfdB
アスタリスク (*) または疑問符 (?) を使用して、同じ文字のタグのセットを指定できます。 次のコマンドは、 Afd で始まるプール タグを持つ割り当てを表示します。これは、afd.sysで使用されるタグです。
poolmon /iAfd*
PoolMon スタートアップ コマンドには、複数の /i パラメーターと /x パラメーターを 含めることができます。 次のコマンドは、タグが Aud で始まり、Cc で始まる 4 文字のタグを持つ割り当てを表示します。ただし、CcBc タグを使用した割り当てを除きます。
poolmon /iAud* /iCc?? /xCcBc
更新の間の値の変更によって、PoolMon の表示を並べ替えることもできます。 /( パラメーターは、PoolMon を変更順に並べ替えモードにします。
次のコマンドは、 Afd で始まるタグで割り当てを表示し、割り当ての変更によって並べ替えます。 /a パラメーターを使用して割り当ての数で並べ替え、/) パラメーターを使用して割り当ての数の変更で並べ替えます。
poolmon /iAfd* /( /a
/( パラメーターとかっこキーはトグル スイッチです。 PoolMon が変更順の並べ替えモードの場合、すべての並べ替えコマンドが、値の変更によって並べ替えるコマンドとして解釈されます。 開きかっこキーをもう一度押すと、値で並べ替えられます。
例 2: ディスプレイ ドライバー名
PoolMon /g パラメーターを使用すると、Windows コンポーネントの名前と、各プール タグを割り当てる一般的に使用されるドライバーを表示できます。 特定のタグを使用した割り当てで問題が見つかると、この機能は問題のあるコンポーネントまたはドライバーを特定するのに役立ちます。
コンポーネントとドライバーは、Mapped_Driver列 (ディスプレイの右端の列) に一覧表示されます。 Mapped_Driver列のデータは、WDK と共にインストール pooltag.txtファイルから取得されます。
次のコマンドは、 NtF で始まるタグで割り当てられたメモリを表示します。 (疑問符文字 (?) をワイルドカードとして使用します)。 /g パラメーターは、Mapped_Driver列を追加します。
poolmon /iNtF? /g "C:\Program Files (x86)\Windows Kits\10\Debuggers\x64\triage\pooltag.txt"
pooltag.txt ファイルを poolmon と同じ場所にコピーすることもできます。 これにより、この使用が可能になります。
poolmon /iNtF? /g
結果の表示には、 NtF で始まるタグを含む割り当てが一覧表示されます。 ディスプレイの右端の列 (Mapped_Driver) は、メモリが NTFS ファイル システムのドライバーである ntfs.sysによって割り当てられたことを示しています。 この場合、pooltag.txt には NTFS 割り当てのソース ファイルが含まれているため、表示がさらに具体的になります。
Memory: 260620K Avail: 65152K PageFlts: 85 InRam Krnl: 2116K P:19560K
Commit: 237688K Limit: 640916K Peak: 260632K Pool N: 8500K P:33024K
System pool information
Tag Type Allocs Frees Diff Bytes Per Alloc Mapped_Driver
NtFA Nonp 9112 ( 0) 9112 ( 0) 0 0 ( 0) 0 [ntfs.sys - AttrSup.c]
NtFB Paged 3996 ( 0) 3986 ( 0) 10 252088 ( 0) 25208 [ntfs.sys - BitmpSup.c]
NtFC Paged 1579279 ( 0) 1579269 ( 0) 10 640 ( 0) 64 [ntfs.sys - Create.c]
NtFD Nonp 13 ( 0) 13 ( 0) 0 0 ( 0) 0 [ntfs.sys - DevioSup.c]
NtFF Paged 1128 ( 0) 1128 ( 0) 0 0 ( 0) 0 [ntfs.sys - FileInfo.c]
NtFI Nonp 152 ( 0) 152 ( 0) 0 0 ( 0) 0 [ntfs.sys - IndexSup.c]
NtFL Nonp 68398 ( 0) 68390 ( 0) 8 27280 ( 0) 3410 [ntfs.sys - LogSup.c]
NtFS Paged 2915 ( 0) 2614 ( 0) 301 80192 ( 0) 266 [ntfs.sys - SecurSup.c]
NtFa Paged 838 ( 0) 829 ( 0) 9 288 ( 0) 32 [ntfs.sys - AllocSup.c]
NtFd Paged 137696 ( 0) 137688 ( 0) 8 720 ( 0) 90 [ntfs.sys - DirCtrl.c]
NtFf Nonp 2 ( 0) 1 ( 0) 1 40 ( 0) 40 [ntfs.sys - FsCtrl.c]
NtFs Nonp 48825 ( 0) 47226 ( 0) 1599 64536 ( 0) 40 [ntfs.sys - StrucSup.c]
NtFv Paged 551 ( 0) 551 ( 0) 0 0 ( 0) 0 [ntfs.sys - ViewSup.c]
Pooltag.txt は広範ですが、Windows で使用されるすべてのタグの完全な一覧ではありません。 ディスプレイに表示されるタグが pooltag.txtに含まれていない場合、PoolMon はタグのMapped_Driver列に "不明なドライバー" と表示されます。
次の例は、32 ビット システムでのこのメソッドを示しています。
次のコマンドでは、 /i パラメーターを使用して、MEM で終わるタグを持つ割り当てを一覧表示します。 /g パラメーターは、pooltag.txt ファイルからディスプレイにドライバー名を追加します。
poolmon /i?MEM /g
結果の表示には、タグが MEM で終わる割り当てが一覧表示されます。 ただし、MEM タグは pooltag.txtに含まれていないため、ドライバー名の代わりに "不明なドライバー" がMapped_Driver列に表示されます。
Tag Type Allocs Frees Diff Bytes Per Alloc Mapped_Driver
1MEM Nonp 1 ( 0) 0 ( 0) 1 3344 ( 0) 3344 Unknown Driver
2MEM Nonp 1 ( 0) 0 ( 0) 1 3944 ( 0) 3944 Unknown Driver
3MEM Nonp 3 ( 0) 0 ( 0) 3 248 ( 0) 82 Unknown Driver
次のコマンドは、PoolMon を起動します。 /i パラメーターを使用して、MEM で終わるタグを持つ割り当てを一覧表示します。
poolmon /i?MEM
次のコマンドは、 Ip で始まるタグの割り当てを一覧表示します。 Mapped_Driver列の pooltag.txt ファイルの内容を使用する /g パラメーターを使用します。
poolmon /iIp* /g
結果の表示では、Mapped_Driver列に pooltag.txt ファイルのデータが含まれます。
Memory: 130616K Avail: 23692K PageFlts: 146 InRam Krnl: 2108K P: 9532K
Commit: 187940K Limit: 318628K Peak: 192000K Pool N: 8372K P:13384K
System pool information
Tag Type Allocs Frees Diff Bytes Per Alloc Mapped_Driver
IpEQ Nonp 1 ( 0) 0 ( 0) 1 1808 ( 0) 1808 [ipsec][ipsec.sys - event queue]
IpFI Nonp 26 ( 0) 0 ( 0) 26 7408 ( 0) 284 [ipsec][ipsec.sys - Filter blocks]
IpHP Nonp 1 ( 0) 1 ( 0) 0 0 ( 0) 0 [ipsec.sys - IP Security]
IpIO Nonp 1 ( 0) 1 ( 0) 0 0 ( 0) 0 [ipsec]
IpLA Nonp 1 ( 0) 0 ( 0) 1 248 ( 0) 248 [ipsec][ipsec.sys - lookaside lists]
IpSH Nonp 1 ( 0) 1 ( 0) 0 0 ( 0) 0 [ipsec.sys - IP Security]
IpSI Nonp 1027 ( 0) 0 ( 0) 1027 53272 ( 0) 51 [ipsec][ipsec.sys - initial allcoations]
IpTI Nonp 3 ( 0) 0 ( 0) 3 5400 ( 0) 1800 [ipsec][ipsec.sys - timers]
例 3: メモリリークを検出する
この例では、PoolMon を使用してメモリ リークを検出する手順を示します。
PoolMon を /p /p (ページ プールからの割り当てのみを表示) と /b (バイト数で並べ替える) というパラメーターを指定して開始します。
poolmon /p /p /bPoolMon を数時間実行します。 PoolMon を開始するとデータが変更されるため、データが信頼できる前に安定した状態を回復する必要があります。
PoolMon によって生成された情報をスクリーン ショットとして保存するか、コマンド ウィンドウからコピーしてメモ帳に貼り付けます。
PoolMon に戻り、 p キーを 2 回押すと、非ページ プールからの割り当てのみが表示されます。
少なくとも 2 時間、約 30 分ごとに手順 3 と 4 を繰り返し、毎回ページプールの表示と非ページプールの表示を交互に切り替えます。
データ収集が完了したら、各タグの Diff (割り当て操作から空き操作を除く) とバイト (割り当てられたバイト数から解放されたバイト数を引いたバイト数) の値を調べて、継続的に増加する値に注意してください。
次に、PoolMon を停止し、数時間待ってから、PoolMon を再起動します。
増加していた割り当てを調べて、バイト数が解放されたかどうかを判断します。 原因として考えられるのは、まだ解放されていない割り当て、またはサイズの増加が続いている割り当てです。
例 4: プール のメモリ リークを調べる
次の例は、PoolMon を使用して、疑わしいプリンター ドライバーからのプール メモリ リークを調査する方法を示しています。 この例では、PoolMon は、Windows が Dsrd タグを使用してメモリ割り当てに関して収集するデータを表示します。
一部のプリンター ドライバーは、グラフィカル デバイス インターフェイス (GDI) オブジェクトと関連するメモリを割り当てるときに Drsd タグを割り当てます。 プリンター ドライバーにオブジェクト リークがある場合、Drsd タグで割り当てられたメモリもリークします。
手記 この例の手順を実行する前に、使用しているプリンターが完了するまで中断されないことを確認します。 それ以外の場合は、結果が無効である可能性があります。
コマンドラインで、次のように入力します。
poolmon /iDrsd
このコマンドは、Drsd タグを使用して割り当ての情報を表示するように PoolMon に指示します。 (プール タグでは大文字と小文字が区別されるため、次のようにコマンドを正確に入力してください)。
Diff 列と Bytes 列に値を記録します。 次の例の表示では、Diff の値は 21 で、バイト数は 17472 です。
Memory: 130480K Avail: 91856K PageFlts: 1220 InRam Krnl: 2484K P: 7988K
Commit: 30104K Limit: 248432K Peak: 34028K Pool N: 2224K P: 8004K
Tag Type Allocs Frees Diff Bytes Per Alloc
Drsd Paged 560 ( 177) 539 ( 171) 21 17472 ( 4992) 832
プリンターにジョブを送信し、Windows が正常に戻るのを少し待ってから、Diff 列と Bytes 列の値を記録します。
Memory: 130480K Avail: 91808K PageFlts: 1240 InRam Krnl: 2488K P: 7996K
Commit: 30152K Limit: 248432K Peak: 34052K Pool N: 2224K P: 8012K
Tag Type Allocs Frees Diff Bytes Per Alloc
Drsd Paged 737 ( 0) 710 ( 0) 27 22464 ( 0) 832
プリンター ドライバーのメモリ管理が正常に動作している場合、Diff の値は、印刷後に元の値 21 に戻る必要があります。 ただし、上記の出力が示すように、Diff の値は 27 に増加し、バイト数は 22464 に増加しました。 初期出力と後続出力の違いは、6 つの Drsd ブロック (合計 4992 バイト) が印刷中にリークしたことを意味します。
詳細については、以下を参照してください。
漏洩しているドライバーを特定したと思われる場合は、 Microsoft サポート Web サイトにアクセスし、サポート技術情報で関連する記事を検索するか、サード パーティ製ドライバーの場合はベンダーにお問い合わせください。
例 5: ターミナル サーバー セッションを監視する
この例では、ターミナル サービス セッション プールからの割り当てを表示するいくつかの方法を示します。 これは、/s コマンドラインパラメーターの使用方法と、s、TSSessionID、i の実行パラメーターを示しています。
次のコマンドは、すべてのターミナル サービス セッション プールからの割り当てを表示します。 この例では、ターミナル サーバーとして構成されているローカル コンピューターがセッションをホストしており、クライアント コンピューターはリモート デスクトップ機能を使用してホストに接続しています。
poolmon /s
応答として、PoolMon はすべてのセッション プールからの割り当てを表示します。 ヘッダーの「すべてのセッションプール情報」のタイトルに注意してください。
Memory: 523572K Avail: 233036K PageFlts: 344 InRam Krnl: 1828K P:18380K
Commit: 193632K Limit:1279764K Peak: 987356K Pool N:14332K P:18644K
All sessions pool information
Tag Type Allocs Frees Diff Bytes Per Alloc
Bmfd Paged 361 ( 0) 336 ( 0) 25 57832 ( 0) 2313
DDfb Paged 34 ( 0) 22 ( 0) 12 720 ( 0) 60
Dddp Paged 8 ( 0) 6 ( 0) 2 272 ( 0) 136
Dh 1 Paged 24 ( 0) 24 ( 0) 0 0 ( 0) 0
Dh 2 Paged 344 ( 0) 344 ( 0) 0 0 ( 0) 0
Dvgr Paged 2 ( 0) 2 ( 0) 0 0 ( 0) 0
GDev Paged 108 ( 0) 102 ( 0) 6 20272 ( 0) 3378
GFil Paged 29 ( 0) 27 ( 0) 2 160 ( 0) 80
GPal Paged 11 ( 0) 8 ( 0) 3 816 ( 0) 272
GTmp Paged 88876 ( 1) 88876 ( 1) 0 0 ( 0) 0
GUma Paged 2 ( 0) 2 ( 0) 0 0 ( 0) 0
Galp Paged 3250 ( 0) 3250 ( 0) 0 0 ( 0) 0
Gbaf Paged 9829 ( 0) 9801 ( 0) 28 19712 ( 0) 704
Gcac Paged 3761 ( 0) 3706 ( 0) 55 288968 ( 0) 5253
Gcsl Paged 1 ( 0) 0 ( 0) 1 488 ( 0) 488
Gdbr Paged 6277 ( 0) 6271 ( 0) 6 1872 ( 0) 312
...
特定のセッション プールからの割り当てを確認するには、次のコマンドに示すように、 /s パラメーターの直後にセッション ID を入力します。 このコマンドは、ターミナル サービス セッション 0 のセッション プールの割り当てを表示します。
poolmon /s0
応答として、PoolMon はターミナル サービス セッション 0 のセッション プールからの割り当てを表示します。 ヘッダーの "Session 0 pool information" (セッション 0 プール情報) タイトルをメモします。
Memory: 523572K Avail: 233024K PageFlts: 525 InRam Krnl: 1828K P:18384K
Commit: 193760K Limit:1279764K Peak: 987356K Pool N:14340K P:18644K
Session 0 pool information
Tag Type Allocs Frees Diff Bytes Per Alloc
Bmfd Paged 361 ( 0) 336 ( 0) 25 57832 ( 0) 2313
DDfb Paged 34 ( 0) 22 ( 0) 12 720 ( 0) 60
Dddp Paged 8 ( 0) 6 ( 0) 2 272 ( 0) 136
Dh 1 Paged 24 ( 0) 24 ( 0) 0 0 ( 0) 0
Dh 2 Paged 344 ( 0) 344 ( 0) 0 0 ( 0) 0
Dvgr Paged 2 ( 0) 2 ( 0) 0 0 ( 0) 0
GDev Paged 108 ( 0) 102 ( 0) 6 20272 ( 0) 3378
GFil Paged 29 ( 0) 27 ( 0) 2 160 ( 0) 80
GPal Paged 11 ( 0) 8 ( 0) 3 816 ( 0) 272
GTmp Paged 89079 ( 99) 89079 ( 99) 0 0 ( 0) 0
GUma Paged 2 ( 0) 2 ( 0) 0 0 ( 0) 0
Galp Paged 3250 ( 0) 3250 ( 0) 0 0 ( 0) 0
Gbaf Paged 9830 ( 0) 9802 ( 0) 28 19712 ( 0) 704
Gcac Paged 3762 ( 0) 3707 ( 0) 55 283632 ( 0) 5156
Gcsl Paged 1 ( 0) 0 ( 0) 1 488 ( 0) 488
Gdbr Paged 6280 ( 0) 6274 ( 0) 6 1872 ( 0) 312
...
セッション プールからメモリを割り当てるドライバーとコンポーネントを特定するには、次のコマンドに示すように /g パラメーターを追加します。 /g パラメーターは、各タグを割り当てる Windows コンポーネントとドライバーを一覧表示するMapped_Driver列を追加します。
poolmon /s0 /g
Memory: 523572K Avail: 235876K PageFlts: 43 InRam Krnl: 1900K P:18860K
Commit: 185040K Limit:1279764K Peak: 987356K Pool N:14684K P:19124K
Session 0 pool information
Tag Type Allocs Frees Diff Bytes Per Alloc Mapped_Driver
Bmfd Paged 421 ( 0) 396 ( 0) 25 57832 ( 0) 2313 [Font related stuff]
DDfb Paged 34 ( 0) 22 ( 0) 12 720 ( 0) 60 Unknown Driver
Dddp Paged 11 ( 0) 6 ( 0) 5 392 ( 0) 78 Unknown Driver
Dh 1 Paged 37 ( 0) 35 ( 0) 2 224 ( 0) 112 Unknown Driver
Dh 2 Paged 367 ( 0) 364 ( 0) 3 912 ( 0) 304 Unknown Driver
Dvgr Paged 2 ( 0) 2 ( 0) 0 0 ( 0) 0 [vga for risc video driver]
GDev Paged 119 ( 0) 113 ( 0) 6 20272 ( 0) 3378 [Gdi pdev]
GFil Paged 29 ( 0) 27 ( 0) 2 160 ( 0) 80 [Gdi engine descriptor list]
GPal Paged 11 ( 0) 8 ( 0) 3 816 ( 0) 272 [Gdi Objects]
GTmp Paged 98626 ( 1) 98626 ( 1) 0 0 ( 0) 0 [Gdi Objects]
GUma Paged 2 ( 0) 2 ( 0) 0 0 ( 0) 0 [Gdi Objects]
Galp Paged 3250 ( 0) 3250 ( 0) 0 0 ( 0) 0 [Gdi Objects]
Gbaf Paged 10331 ( 0) 10305 ( 0) 26 18304 ( 0) 704 [Gdi Objects]
Gcac Paged 4722 ( 0) 4666 ( 0) 56 305400 ( 0) 5453 [Gdi glyph cache]
Gcsl Paged 1 ( 0) 0 ( 0) 1 488 ( 0) 488 [Gdi string resource script names]
Gdbr Paged 6972 ( 0) 6965 ( 0) 7 2184 ( 0) 312 [Gdi driver brush realization]
PoolMon の実行中にターミナル サービス セッション プールの表示を構成することもできます。 次の表は、一連の実行中のコマンドを入力順に示し、結果として得られる PoolMon の表示を示しています。
シリーズは、PoolMon を開始するコマンドで始まります。 他のすべてのパラメーターは、PoolMon の実行中に入力されます。
poolmon
| 鍵 | 結果 | 説明 |
|---|---|---|
s |
すべてのセッション プールを表示します。 |
|
s |
システム プールを表示します。 |
s パラメーターは、システム・プールとターミナル・サービス・セッション・プールの間の表示を切り替えます。 |
0 |
セッション 0 プールを表示します。 |
システム プールの表示中にセッション ID を入力できます。 |
7 |
セッション 7 プールを表示します。 |
|
a |
セッション 7 のプール割り当てを割り当て数で並べ替え、表示します。 |
すべての標準実行パラメーターは、セッション プールの表示に対して有効です。 |
0 |
セッション 0 の割り当てを割り当て数で並べ替え、表示します。 |
セッションと並べ替えのオプションは、変更されるまで保持されます。 |
s |
システム プールを表示します。 |
|
s |
セッション 0 の割り当てを割り当て数で並べ替え、表示します。 |
セッション オプションは保持されます。 |
10ENTER |
セッション 1 の割り当てを表示し、セッション 0 の割り当てを表示します。 |
i がない場合は、セッション ID 0 から 9 のみを入力できます。 |
i |
ターミナル サーバー セッション ID の入力を求めるメッセージが表示されます。 |
|
"10" |
セッション 10 の割り当てを表示します。 |
|
i |
ターミナル サーバー セッション ID の入力を求めるメッセージが表示されます。 |
すべてのセッション プールを表示するには、 i キーを押してから Enter キーを押します。 |
入る |
すべてのセッション プールを表示します。 |
ターミナル サーバーとして構成されたシステムのみが、セッション プールからメモリを割り当てます。 PoolMon を使用して、ターミナル サーバーではないコンピューターにセッション プールを表示する場合、または Windows に存在しないセッション ID を入力した場合、PoolMon は割り当てを表示しません。 代わりに、一般的なメモリ データを含む見出しのみが表示されます。
次のコマンドは、すべてのターミナル サービス セッション プールからの割り当てを表示します。
poolmon /s
次の図は、 /s コマンドがターミナル サーバーとして構成できなかった Windows XP を実行しているコンピューターに送信された場合に発生する PoolMon の表示を示しています。
Memory: 260620K Avail: 44956K PageFlts: 308 InRam Krnl: 2744K P:20444K
Commit: 185452K Limit: 640872K Peak: 192472K Pool N: 8112K P:20648K
All sessions pool information
Tag Type Allocs Frees Diff Bytes Per Alloc