🦘
PowerShellでダブルホップ問題の手軽な回避策
PowerShellのダブルホップ問題とは
セキュリティ上の理由から、リモート接続先からさらに別のPCへのリモートアクセスが制限される問題です
- ServerA にログインしています。
- ServerA からリモート PowerShell セッションを開始して ServerB に接続します。
- PowerShell リモート処理セッションを介して ServerB で実行するコマンドは、ServerC 上のリソースにアクセスを試みます。
- PowerShell リモート処理セッションの作成に使った資格情報は ServerB から ServerC に渡されないため、ServerC 上のリソースへのアクセスは拒否されます。
ダブルホップ、セカンドホップ、マルチホップなど呼称が統一されていなさそうでした
さすがに不便すぎるためかマイクロソフト公式にいくつか回避策が載っています
うまくいった手軽な方法
RunAs を使用する PSSessionConfigurationがうまく行きました
RunAs*を指定したConfigurationでPSSessionを作成するとダブルホップ問題が回避できるようです
このためのInvoke-PSSessionというモジュールがPowerShell Galleryにあるのでこれを利用すると簡単にできました
Install-Module Invoke-PSSession
$Session = Invoke-PSSession -ComputerName $ServerB -Credential Get-Credential
Invoke-Command -Session $Session -ScriptBlock {
hostname
Invoke-Command -ComputerName $ServerC -Credential Get-Credential -ScriptBlock {
hostname
}
}
ソースを見るとInvoke-PSSession
は、
- 一度
Invoke-Command
でリモートに入り -
-RunAsCredential
付きのPSSessionConfiguration
を登録し - 改めてその
PSSessionConfiguration
を指定してセッションを作成して返す
という挙動になっていました
弱点としてはユーザー名と同じ名前のPSSessionConfiguration
がサーバーBに登録されたままになるので、セキュリティを気にするなら後で消しといたほうがよさそうです
ダメだったほかの方法
CredSSP
回避策として一番おすすめされているのがCredSSPを使う方法ですが、
事前に次の設定が必要そうで断念しました
- サーバー、クライアント側両方でPowerShellのコマンドで許可が必要
- グループポリシーの設定
*こちらの記事がわかりやすかったです
Invoke-Command スクリプト ブロックの内部で資格情報を渡す
Credential
をInvoke-Command
内に渡してしまう方法です
# This works without delegation, passing fresh creds
# Note $Using:Cred in nested request
$cred = Get-Credential Contoso\Administrator
Invoke-Command -ComputerName ServerB -Credential $cred -ScriptBlock {
hostname
Invoke-Command -ComputerName ServerC -Credential $Using:cred -ScriptBlock {hostname}
}
これができれば一番よかったのですが手元の環境では動作しませんでした
とあるので以前は動作したけど、今はダメになったとかなのかもしれません
参考
Discussion