运行 具有相对路径的 PsExec
Run PsExec with relative Path
我对标题感到抱歉,但我不确定如何解释。
我尝试使用 PsExec 运行 远程计算机上的脚本。
C:\static\path\to\thePSTools\Folder\PsTools\PsExec.exe $IPAddress -i -s -u $Login -p $LoginPassword Powershell $PathToFile
但是我可以 运行 像上面的代码一样编写 PsExec 命令,意思是,
运行从绝对路径执行 PsExec。
问题是当我的程序安装在另一台机器上时,我不知道我的 PsExec 的静态路径。所以我需要一个相对路径。
我尝试了一些方法,但 none 有效
像这样 Push-Location :
Push-Location $PSToolsPath PsExec.exe $IPAddress /accepteula $PathToFile
或者像这样的东西:
$Path + PsExec.exe $IPAddress /accepteula $PathToFile
但是我不能运行。
我知道如何获取相对路径,但问题是如何运行,或者甚至可能。
我愿意对我的问题进行任何修改。因为解释起来有点复杂。
提前致谢
不要使用 PSExec
。虽然有用,PSExec
是一个 CLI 程序,用于 运行ning 命令超过 WinRM
。 PowerShell 已经内置了 PSRemoting
(WinRM
是 PSRemoting
的 backbone),您可以使用 New-PSSession
、Enter-PSSession
、Invoke-Command
,等等,以便访问您控制访问的远程机器:
Note: You must use a server name to connect to the server by default. If the server is not part of your domain or you want to use an IP, you must configure your local WinRM
settings to trust that IP or server name. Alternatively, you can configure WinRM over SSL
to avoid having to trust servers by IP, but your client server will need to both trust the certificate presented by WinRM over SSL
, and the Subject or Subject-Alternative Name of the certificate must validate based on the name or IP you connect with.
WinRM
and PSRemoting
do not allow you to ignore SSL errors.
# Your remote machine credential
$cred = Get-Credential
# Run commands in a one off remote session
Invoke-Command -ComputerName $serverName -Credential $cred { "hello" }
# Create a PSSession so we can run commands over the same session at different times
$session = New-PSSession -ComputerName $serverName -Credential $cred
# Invoke-Command with an existing PSSession
Invoke-Command -ComputerName $serverName -Credential $cred -Session $session { "hello" }
# Enter-PSSession lets you open an interactive terminal within a remote PowerShell session
Enter-PSSession -ComputerName $serverName -Credential $cred -Session $session
# To leave a PSSession you've entered with Enter-PSSession
Exit-PSSession
exit
请注意 exit
不是 Exit-PSSession
的别名,它在您退出远程会话时与退出本地会话时具有相同的效果。
如果您必须使用 PSExec
(例如,PSRemoting
不会让您直接作为 SYSTEM
用户使用 运行 东西,但是 PSExec
确实),那么执行 psexec.exe
:
必须满足以下两个条件之一
The following is not just true for PSExec
, but for any program run on Windows, MacOS, or Windows due to their Unix roots or influences. Each one shares the PATH
concept, and without this, you must know where the program exists on disk or "you ain't runnin' it".
psexec.exe
必须存在于定义的目录之一中 $env:PATH
- 您必须知道从当前目录到
psexec.exe
的绝对或相对路径
- 你所说的“静态路径”实际上是所谓的“绝对路径”,它从驱动器根目录开始,例如
C:\path\to\psexec.exe
。
- 相对路径是从当前目录开始的路径,没有 从驱动器根目录开始,例如
..\..\path\to\psexec.exe
.
如果您不知道该程序的安装位置并且它不在 PATH
上,您唯一的其他选择是从媒体复制或下载您知道它将存储在磁盘上的位置。
嗯...我撒了点谎
如果您确定 psexec.exe
(或其他程序)存在于系统中,则有一种方法可以找到它。您可以在文件系统中搜索它。您拥有的文件越多,IOPS 越低,将延长完成搜索所需的时间。如果找到可执行文件,则可以使用调用运算符 &
:
来执行它
Warning: Be careful with this approach. If multiple executables exist which have the same name but are different versions or different programs entirely, you could accidentally end up executing the wrong version, wrong program altogether, or worst-case scenario, a malicious actor could place a modified or fake psexec.exe
designed to steal your credentials or otherwise cause damage to your environment. You have been warned.
If you go this route, check the known checksum of the program you search for. The below example does not include this but you can use Get-FileHash
to obtain a found psexec.exe
's checksum, and compare it to the known correct checksum.
$foundPsExec = Get-ChildItem C:\ -Recurse -File -Include psexec.exe -EA Continue |
Select-Object -First 1
if( $foundPsExec ) {
& $foundPsExec.FullName
}
请允许我从上面的例子中解释一些事情:
Get-ChildItem
将在文件系统中搜索您提供的路径中的文件。
-Recurse
将允许 Get-ChildItem
在搜索时遍历子目录。
-File
仅 returns FileInfo
个对象
-EA
对于 -ErrorAction
是 shorthand。我们希望确保此行为设置为继续此操作,因为在搜索整个磁盘时,您一定会遇到一些权限错误。
您可以使用 -ErrorAction SilentlyContinue
来隐藏它们,或者让 PowerShell 使用 -ErrorAction Ignore
.
一起丢弃任何错误
- 这使用
Select-Object
仅将 PSExec
的第一个实例分配给变量。如果你使用这个解决方案,你应该实施一些更安全的检查,我只是提供这个作为确保你在使用 &
. 执行时只使用一条路径的例子
- 如果
$foundPsExec
有一个值,运行 它带有绝对路径(这是用 FileInfo.FullName
引用的,因此 FullName
属性 引用。
我对标题感到抱歉,但我不确定如何解释。
我尝试使用 PsExec 运行 远程计算机上的脚本。
C:\static\path\to\thePSTools\Folder\PsTools\PsExec.exe $IPAddress -i -s -u $Login -p $LoginPassword Powershell $PathToFile
但是我可以 运行 像上面的代码一样编写 PsExec 命令,意思是, 运行从绝对路径执行 PsExec。
问题是当我的程序安装在另一台机器上时,我不知道我的 PsExec 的静态路径。所以我需要一个相对路径。 我尝试了一些方法,但 none 有效
像这样 Push-Location :
Push-Location $PSToolsPath PsExec.exe $IPAddress /accepteula $PathToFile
或者像这样的东西:
$Path + PsExec.exe $IPAddress /accepteula $PathToFile
但是我不能运行。
我知道如何获取相对路径,但问题是如何运行,或者甚至可能。
我愿意对我的问题进行任何修改。因为解释起来有点复杂。 提前致谢
不要使用 PSExec
。虽然有用,PSExec
是一个 CLI 程序,用于 运行ning 命令超过 WinRM
。 PowerShell 已经内置了 PSRemoting
(WinRM
是 PSRemoting
的 backbone),您可以使用 New-PSSession
、Enter-PSSession
、Invoke-Command
,等等,以便访问您控制访问的远程机器:
Note: You must use a server name to connect to the server by default. If the server is not part of your domain or you want to use an IP, you must configure your local
WinRM
settings to trust that IP or server name. Alternatively, you can configureWinRM over SSL
to avoid having to trust servers by IP, but your client server will need to both trust the certificate presented byWinRM over SSL
, and the Subject or Subject-Alternative Name of the certificate must validate based on the name or IP you connect with.
WinRM
andPSRemoting
do not allow you to ignore SSL errors.
# Your remote machine credential
$cred = Get-Credential
# Run commands in a one off remote session
Invoke-Command -ComputerName $serverName -Credential $cred { "hello" }
# Create a PSSession so we can run commands over the same session at different times
$session = New-PSSession -ComputerName $serverName -Credential $cred
# Invoke-Command with an existing PSSession
Invoke-Command -ComputerName $serverName -Credential $cred -Session $session { "hello" }
# Enter-PSSession lets you open an interactive terminal within a remote PowerShell session
Enter-PSSession -ComputerName $serverName -Credential $cred -Session $session
# To leave a PSSession you've entered with Enter-PSSession
Exit-PSSession
exit
请注意 exit
不是 Exit-PSSession
的别名,它在您退出远程会话时与退出本地会话时具有相同的效果。
如果您必须使用 PSExec
(例如,PSRemoting
不会让您直接作为 SYSTEM
用户使用 运行 东西,但是 PSExec
确实),那么执行 psexec.exe
:
The following is not just true for
PSExec
, but for any program run on Windows, MacOS, or Windows due to their Unix roots or influences. Each one shares thePATH
concept, and without this, you must know where the program exists on disk or "you ain't runnin' it".
psexec.exe
必须存在于定义的目录之一中$env:PATH
- 您必须知道从当前目录到
psexec.exe
的绝对或相对路径- 你所说的“静态路径”实际上是所谓的“绝对路径”,它从驱动器根目录开始,例如
C:\path\to\psexec.exe
。 - 相对路径是从当前目录开始的路径,没有 从驱动器根目录开始,例如
..\..\path\to\psexec.exe
.
- 你所说的“静态路径”实际上是所谓的“绝对路径”,它从驱动器根目录开始,例如
如果您不知道该程序的安装位置并且它不在 PATH
上,您唯一的其他选择是从媒体复制或下载您知道它将存储在磁盘上的位置。
嗯...我撒了点谎
如果您确定 psexec.exe
(或其他程序)存在于系统中,则有一种方法可以找到它。您可以在文件系统中搜索它。您拥有的文件越多,IOPS 越低,将延长完成搜索所需的时间。如果找到可执行文件,则可以使用调用运算符 &
:
Warning: Be careful with this approach. If multiple executables exist which have the same name but are different versions or different programs entirely, you could accidentally end up executing the wrong version, wrong program altogether, or worst-case scenario, a malicious actor could place a modified or fake
psexec.exe
designed to steal your credentials or otherwise cause damage to your environment. You have been warned.If you go this route, check the known checksum of the program you search for. The below example does not include this but you can use
Get-FileHash
to obtain a foundpsexec.exe
's checksum, and compare it to the known correct checksum.
$foundPsExec = Get-ChildItem C:\ -Recurse -File -Include psexec.exe -EA Continue |
Select-Object -First 1
if( $foundPsExec ) {
& $foundPsExec.FullName
}
请允许我从上面的例子中解释一些事情:
Get-ChildItem
将在文件系统中搜索您提供的路径中的文件。-Recurse
将允许Get-ChildItem
在搜索时遍历子目录。-File
仅 returnsFileInfo
个对象-EA
对于-ErrorAction
是 shorthand。我们希望确保此行为设置为继续此操作,因为在搜索整个磁盘时,您一定会遇到一些权限错误。您可以使用
一起丢弃任何错误-ErrorAction SilentlyContinue
来隐藏它们,或者让 PowerShell 使用-ErrorAction Ignore
.
- 这使用
Select-Object
仅将PSExec
的第一个实例分配给变量。如果你使用这个解决方案,你应该实施一些更安全的检查,我只是提供这个作为确保你在使用&
. 执行时只使用一条路径的例子
- 如果
$foundPsExec
有一个值,运行 它带有绝对路径(这是用FileInfo.FullName
引用的,因此FullName
属性 引用。