OverTheWire.org
Hacker Community
Want to help out OverTheWire ?
Volunteer ? Donate ?
Click here!
Discuss this level on the forum

Level 9

Tunneling your firewall
How do you get data through a firewall that is blocking any tcp connection? You just don't use a tcp connection, but instead other packets, that might not be filtered. For example network maintenance protocols like ICMP.

There is a raw socket open on a yet unknown host that listens for icmp packets and forwards them to a tcp server that you cannot reach. Your job is to create a client that communicates with this icmp "server". If everything works, you find yourself in a shell on an unknown system, and can search for the password.

The protocol and the server, that is used by the ICMP tunnel is described in your home directory. If you manage to blackbox analyze it, then you can jump directly from semtex0 to semtex10 :)

You will have to use /rdx/rawwrapper.
Code listing (level9.rawwrapper.c)
 1 #ifndef _GNU_SOURCE
 2 #define _GNU_SOURCE
 3 #endif
 4 #include <unistd.h>
 5 #include <stdio.h>
 6 #include <stdlib.h>
 7 #include <netinet/ip_icmp.h>
 8 #include <string.h>
 9 
10 
11 #define DROPUID 1009
12 #define DROPGID 1009
13 
14 // rawwrapper, aton 2004
15 
16 int main(int argc, char *argv[])
17 {
18         int rfd;
19         char *argv0, *argv1;
20 
21         if (argc<2)
22         {
23                 printf("usage: rawwrapper <program>\n");
24                 printf("argv[1] will be the raw socket\n");
25                 exit(EXIT_FAILURE);
26         }
27 
28         //open raw socket
29         if ((rfd = socket(PF_INET, SOCK_RAW, IPPROTO_ICMP))<0)
30         {
31                 perror("socket");
32                 return EXIT_FAILURE;
33         }
34 
35         //drop priviledges
36         setresgid(DROPGID, DROPGID, DROPGID);
37         setresuid(DROPUID, DROPUID, DROPUID);
38 
39         argv0=malloc(strlen(argv[0])+1);
40         strcpy(argv0, argv[0]);
41         argv1=malloc(strlen(argv[1])+1);
42         strcpy(argv1, argv[1]);
43 
44         // fill in new argv
45         argv[0]=argv1;
46         sprintf(argv[1], "%d", rfd);
47 
48         //execute the client program
49         execve(argv[0], argv, NULL);
50         return EXIT_SUCCESS;
51 }