PowerShellを使ってアプリケーションの異常終了を報告する方法

PowerShellを使ってアプリケーションの異常終了を報告する方法の手順を先に要約すると「異常終了の報告はprocess不在判定ではなく、Get-WinEventでApplication ErrorやWindows Error Reportingのeventを取得し、時刻、event ID、application version、fault module、例外codeを最小限に記録します。」となります。対象環境はprocessが見つからないことをcrashと断定せず、Application ErrorやWER eventを時刻・process・fault moduleで確認する構成です。

目次

調査時間窓と対象applicationを固定する

アプリクラッシュ調査では、対象実行ファイル名と発生時間帯を固定し、Application ErrorやWindows Error ReportingのRecordId、Provider、Event ID、XMLフィールドを取得します。同じ障害を時刻だけで結び付けず、Faulting Application、Module、Report IDを照合し、重複イベントを一件に集約します。

  • 対象applicationの正式exe名とversionを確認する
  • crash発生時刻とtimezone、user操作を記録する
  • Application logのProviderNameとevent IDを確認する
  • dumpやreportに個人情報が含まれるため保存先を確認する

Application Error 1000をserver側で絞る

event取得は読み取りです。旧Send-MailMessageは新規設計の既定にせず、組織の承認済みnotification基盤へ最小reportを送ります。SMTP credentialをscriptへ記載しません。dumpにはmemory上のsecretが含まれるため、収集範囲、暗号化、ACL、保持期限をincident手順に従います。crash原因調査中にsecurity設定を無効化しません。

WER eventを近接時刻で補足する

Application Errorを期間検索

$start=(Get-Date).AddHours(-2)
Get-WinEvent -FilterHashtable @{LogName='Application';ProviderName='Application Error';Id=1000;StartTime=$start} -MaxEvents 100 |
  Select-Object TimeCreated,RecordId,Id,Message

IDとproviderを組にします。messageから必要項目だけ抽出します。

WER eventを補足

Get-WinEvent -FilterHashtable @{LogName='Application';ProviderName='Windows Error Reporting';StartTime=$start} -MaxEvents 100 |
  Select-Object TimeCreated,Id,RecordId,Message

同時刻のApplication Errorと相関します。

process不在を別状態で扱う

$p=Get-Process -Name 'notepad' -ErrorAction SilentlyContinue
if($p){$p | Select-Object Id,StartTime,Path}else{'NotRunningAtCheckTime'}

NotRunningAtCheckTimeはcrash証拠ではありません。正常終了や未起動も含みます。

report objectを作る

$event=Get-WinEvent -FilterHashtable @{LogName='Application';ProviderName='Application Error';Id=1000} -MaxEvents 1
[pscustomobject]@{Host=$env:COMPUTERNAME;Time=$event.TimeCreated;RecordId=$event.RecordId;EventId=$event.Id} | Export-Csv '.\crash-summary.csv' -NoTypeInformation

message全文やuser dataを既定で含めません。

crash対象EXEの署名を確認

Get-AuthenticodeSignature -LiteralPath 'C:\Program Files\Target\target.exe' | Select-Object Status,SignerCertificate

対象pathはeventとinventoryから確認します。

現在のprocess状態を過去crashと分ける

process不在は異常終了、正常終了、未起動、別user sessionのいずれでも起こります。event ID 1000はcrashの手掛かりで、faulting moduleやexception codeをvendor資料と照合します。同一crashから複数eventが生成される場合があり、件数はRecordIdと時刻でdeduplicateします。

event XMLから必要項目だけ保存する

  • process不在をcrashと断定する
  • event IDだけ見てproviderを無視する
  • Message全文をmailする
  • credentialをscriptへ埋め込む
  • 複数eventを別crashとして数える

dump設定変更を収集手順から切り離す

Event Viewer、WER history、application log、監視alertの時刻とversionを照合します。正常終了、未起動、実crashをtest環境で区別し、reportが必要項目だけを持つことをreviewします。通知失敗でもevidenceを失わず再送可能にします。

RecordId・時刻・process identityを検収する

Application Error event 1000とWindows Error Reporting eventをTimeCreated、faulting application、module、exception code、report IDで相関します。process不在はcrash後の通常状態になり得るため、event 0件・process終了・取得errorを別にします。

Application Error eventを上限付きで収集する

$start=(Get-Date).AddHours(-2)
$events=@(Get-WinEvent -FilterHashtable @{LogName='Application';ProviderName='Application Error';Id=1000;StartTime=$start} -MaxEvents 100 -ErrorAction Stop)
$events | Select-Object TimeCreated,RecordId,Id,ProviderName,@{n='Xml';e={$_.ToXml()}}

crash eventの有無をquery成否と独立評価する

  • crash event取得:指定期間のeventからRecordIdとXML fieldを取得し、同一crash候補を時刻/名前/report IDで対応付ける
  • 期間内crashなし:event 0件は調査期間内に記録なしとして扱い、crash否定にはしない
  • event・signature error:log access、event schema差、missing executable、signature errorはEvidenceGapとして残す

localized Messageのregexだけでfieldを抽出せずToXmlのData名を確認します。WER archiveにはdumpや個人情報が含まれ得るため、本文を広くcopyせず最小metadataに限定します。

process不在と複数crashを試す

$p=Get-Process -Name 'notepad' -ErrorAction SilentlyContinue
[pscustomobject]@{ProcessState=if($p){'Running'}else{'NotRunning'};CrashEvents=$events.Count;WindowStart=$start}

event 0/1/複数、same-name process、schema欠損、unsigned exeをtestします。host/timezone、RecordId、event XML field、exe hash/signature、相関ruleを保存します。

現在processが動いていることは、時間窓内にcrashがなかった証拠ではありません。Application ErrorとWERを時刻・実行file・faulting moduleで相関し、dump収集の有効化は別承認にします。

公式情報・参考資料

この記事を書いた人

実務の現場で詰まりがちなポイントを地図にするITブログ「IT trip」を運営。Windows/Office(Teams・Excel)からSQL、サーバ運用、ガジェットまで、再現性のある手順と“なぜそうなるか”を丁寧に解説します。読んだらすぐ試せること、そして迷った人の次の一歩が見えることを大切にしています。

コメント

コメントする

目次