PowerShell を使用した証明書ストアの管理
私たちが Windows システム管理者だった場合、Windows 証明書を使用することを余儀なくされた可能性があります。 残念ながら、Windows で証明書を操作することは、通常、システム管理者が引き受けなければならないさまざまな作業の 1つです。
この記事では、PowerShell を使用して証明書を照会し、証明書ストアを管理する方法について説明します。
証明書ストアについて
証明書ストアは、Windows OS が現在インストールされているすべての証明書を保持するバケット
です。 証明書は複数のストアに存在することができ、物理ストアまたは論理ストアと呼ばれることもあります。 レジストリ キーとファイルは、既存のファイル システムまたはレジストリの場所を参照する物理ストアに格納されます。
Windows レジストリとファイル システムには、各ストアが含まれます。 証明書を操作するときは、レジストリやファイル システムではなく、論理ストアと対話します。
1つ以上の物理ストアへの動的参照は論理ストアであり、物理ストアは論理ストアよりも管理が困難です。 Windows は、ユーザー コンテキストとコンピューター コンテキストの 2つの場所に証明書を保持します。
証明書が単一のユーザー、複数のユーザー、またはマシン自体によって使用されるかどうかに応じて、証明書はこれら 2つのコンテキストのいずれかに配置されます。 ユーザーまたはコンピューターのコンテキストでの証明書は、この記事の残りの部分ではユーザー証明書およびコンピューター証明書と呼ばれます。
ユーザー証明書
証明書を 1 人のユーザーのみに使用させたい場合は、Windows 証明書マネージャーに格納されているユーザー証明書が理想的です。 これは、有線 IEEE 802.1x
などの証明書ベースの認証システムでは一般的です。
ユーザー証明書は現在のユーザーのプロファイルに保存され、そのユーザーのコンテキストにのみ論理的にマップできます。 同じシステム上でも、ユーザー証明書はマッピング
されており、各ユーザーに固有です。
コンピュータ証明書
すべてのユーザーがコンピューターまたはシステム プロセスで証明書を使用する場合、証明書はコンピューター コンテキストのストア内に配置する必要があります。 たとえば、システムが Web サーバー上の証明書を使用してすべてのクライアントの通信を暗号化する場合、コンピューター コンテキストのストアに証明書を設定するのが理想的です。
コンピューターの証明書ストアがすべてのユーザー コンテキストに対して論理的にマップされていることがわかります。この概念により、コンピューターの証明書ストア内の証明書をすべてのユーザーが使用できるようになります。 ただし、秘密鍵に構成されたアクセス許可に依存します。
Program Data フォルダーと Local Machine Registry ハイブには、コンピューター証明書が含まれています。 さらに、ユーザー証明書は、AppData
フォルダーと Current User Registry
ハイブにあります。
PowerShell を使用した証明書の管理
MMC と同様に、PowerShell を使用して証明書を表示および管理することもできます。 ただし、最初に、物理ストア (レジストリとファイル システム) の証明書を調べてみましょう。
実店舗
Get-ChildItem
PowerShell コマンドレットを使用して、親 HKCU:\Software\Microsoft\SystemCertificates\CA\Certificates\
レジストリ キー パス内のすべてのキーと値を列挙できます。
以下のコマンドは、中間証明機関の論理ストアに現在ログインしているすべてのユーザーの証明書を列挙します。
コード例:
Get-ChildItem -Path HKCU:\Software\Microsoft\SystemCertificate\CA\Certificates\
信頼された CA の証明書の拇印と、対応するプロパティ内のその証明書は、表示されるレジストリ ハイブ内の各エントリに対応します。
出力:
Hive: HKEY_CURRENT_USER\Software\Microsoft\SystemCertificates\CA\Certificates
Name Property
---- --------
070A726C6E4418DCF0213874F0C16D Blob : {3, 0, 0, 0...}
93B041E935
104C63D2546B8021DD105E9FBA5A8D Blob : {3, 0, 0, 0...}
78169F6B32
<SNIP>
個人用ストアは別の標準的なストアであり、このストアの証明書はレジストリではなくファイル システムに格納されます。 以下のコマンドは、個人の現在のユーザー ストアにインストールされている証明書に対応するファイルを含むディレクトリを返します。
Get-ChildItem -Path $env:APPDATA\Microsoft\SystemCertificate\My\Certificates\
以下のコマンドで返される各ファイルは、キー ストレージ プロバイダー (KSP) によって作成された秘密キーのオブジェクトを参照します。 ファイル名は、証明書のサブジェクト キー識別子に対応します。
したがって、インストールする各秘密鍵には、対応するファイルが追加されます。
Get-ChildItem -Path $env:APPDATA\Microsoft\SystemCertificate\My\Keys\
以下のコマンドによって生成されるディレクトリ内の各ファイルは、KSP の暗号化された秘密鍵の一意のコンテナーです。 ファイル名と証明書には直接のリンクはありませんが、ファイルは前のコマンドのポインターのターゲットです。
Get-ChildItem -Path $env:APPDATA\Microsoft\Crypto\Keys
論理ストア
物理パスで証明書を操作することは一般的ではないため、残りのインスタンスには論理ストレージを使用します。 PowerShell は、証明書を物理ストアにマップする Cert:PSDrive
を使用して論理ストアにアクセスできます。
証明書を操作する場合、特定の操作を実行する資格情報をフィルター処理して選択する方法が必要になります。 たとえば、特定の拡張子の値に基づいて証明書を選別して選択します。
次の例では、ルート CA ストアにインストールされているすべての証明書を一覧表示することから始める必要があります。
Get-ChildItem -Path Cert:\CurrentUser\Root\
返されるオブジェクトは証明書オブジェクトであり、以下の例で利用できます。 証明書オブジェクトには、プロパティとして共通の拡張機能が既にあります。
以下の例では、Get-Member
を使用して、返されたオブジェクトのすべてのプロパティを一覧表示します。
コード例:
# gci is an alias of Get-ChildItem
gci -Path Cert:\CurrentUser\Root | Get-Member -MemberType Properties
出力:
TypeName: System.Security.Cryptography.X509Certificates.X509Certificate2
Name MemberType Definition
---- ---------- ----------
PSChildName NoteProperty string PSChildName=EBE112F56D5FE0BA23289319C89D7784A10CEB61
PSDrive NoteProperty PSDriveInfo PSDrive=Cert
PSIsContainer NoteProperty bool PSIsContainer=False
<SNIP>
出力からわかるように、さまざまな拡張機能が、探している証明書を見つけるのに役立ちます。 拡張機能には、証明書が誰に付与されたか、何に使用できるかなど、証明書に関する詳細が含まれます。
証明書テンプレートなど、より複雑なユースケースで使用される他の拡張機能を備えた証明書を探す必要があります。 問題は、これらの拡張機能の値が整数の配列として返され、これらの整数が ASN.1
でエンコードされたコンテンツを表していることです。
この関係を確認するために、以下のコマンドでキー使用法を手動でフェッチします。
((gci -Path Cert:\CurrentUser\Root\ | select -First 1).Extensions | Where-Object {$_.Oid.FriendlyName -eq "Key Usage"}).format($true)
ASN.1
デコードを行う format メソッドは、上記の命令で導入した新しい要素です。 上記のブール値 (例: $true
) を渡すことで、返されるオブジェクトを単一行にするか複数行にするかを指定します。
以下のコマンドでは、証明書の拇印値を利用します。 拇印の値は Windows PowerShell 変数として設定され、次のコマンドで適切な証明書を選択するために使用されます。
$thumb = "cdd4eeae6000ac7f40c3802c171e30148030c072"
Get-ChildItem -Path Cert:\CurrentUser\Root\ | Where-Object {$_.Thumbprint -eq $thumb}
Marion specializes in anything Microsoft-related and always tries to work and apply code in an IT infrastructure.
LinkedIn