nexmon – Blame information for rev 1

Subversion Repositories:
Rev:
Rev Author Line No. Line
1 office 1 #define _XOPEN_SOURCE 700
2 #define USE_LIBPCAP
3  
4 #include <stdio.h>
5 #include <stdlib.h>
6 #include <argp.h>
7 #include <string.h>
8 #include <byteswap.h>
9 #include <pthread.h>
10 #ifdef USE_LIBPCAP
11 #include <pcap.h>
12 #endif
13  
14 #include <arpa/inet.h>
15 #include <netinet/in.h>
16 #include <sys/types.h>
17 #include <sys/socket.h>
18 #include <unistd.h>
19  
20 #define AS_STR2(TEXT) #TEXT
21 #define AS_STR(TEXT) AS_STR2(TEXT)
22  
23 #ifdef USE_LIBPCAP
24 char *pcap_file_name = NULL;
25 #endif
26  
27 int pid = -1;
28 int portin = 5555;
29 int discard_pcap = 0;
30 int discard_radiotap = 0;
31 pthread_t p1;
32 const char *argp_program_version = VERSION;
33 const char *argp_program_bug_address = "<mschulz@seemoo.tu-darmstadt.de>";
34  
35 static char doc[] = "rawproxy -- program to open a raw socket and forward frames as UDP datagrams.";
36  
37 static struct argp_option options[] = {
38 #ifdef USE_LIBPCAP
39 {"interface", 'i', "INTERFACE", 0, "Interface used as RAW interface."},
40 #endif
41 {"parent", 'p', "PID", 0, "Parent process id to monitor (default no monitor)."},
42 {"out", 'o', "PORT", 0, "Port to use (default: 5555)."},
43 {"header", 'h', 0, 0, "Discard pcap header."},
44 {"radiotap", 'r', 0, 0, "Discard radiotap header."},
45 { 0 }
46 };
47  
48 static error_t
49 parse_opt(int key, char *arg, struct argp_state *state)
50 {
51 switch (key) {
52 #ifdef USE_LIBPCAP
53 case 'i':
54 pcap_file_name = arg;
55 break;
56 #endif
57 case 'p':
58 pid = atoi(arg);
59 break;
60 case 'o':
61 portin = atoi(arg);
62 break;
63 case 'h':
64 discard_pcap = 1;
65 break;
66 case 'r':
67 discard_radiotap = 1;
68 break;
69 default:
70 return ARGP_ERR_UNKNOWN;
71 }
72  
73 return 0;
74 }
75  
76 struct map {
77 struct map *next;
78 unsigned int addr;
79 char *name;
80 };
81  
82 static struct argp argp = { options, parse_opt, 0, doc };
83  
84 #ifdef USE_LIBPCAP
85 void
86 analyse_pcap_file(char *filename)
87 {
88 pcap_t *pcap;
89 char errbuf[PCAP_ERRBUF_SIZE];
90 const unsigned char *packet;
91 struct pcap_pkthdr header;
92 struct bpf_program fp;
93 char *fct_name;
94 int offset = 0, sock;
95 struct iovec iov[2];
96  
97 struct msghdr msg_hdr;
98  
99 struct sockaddr_in sin = {
100 .sin_family = AF_INET,
101 .sin_port = htons(portin),
102 .sin_addr.s_addr = inet_addr("127.0.0.1"),
103 .sin_zero = { 0 }
104 };
105  
106  
107 sock = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
108  
109 if(!sock) {
110 printf("ERR: socket\n");
111 return;
112 }
113  
114 if(!strcmp(filename, "wlan0")) {
115 pcap = pcap_open_live("wlan0", BUFSIZ, 1, 0, errbuf);
116 } else if(!strcmp(filename, "any")) {
117 pcap = pcap_open_live("any", BUFSIZ, 1, 0, errbuf);
118 offset = 2;
119 } else {
120 pcap = pcap_open_offline(filename, errbuf);
121 }
122  
123 if(!pcap) {
124 printf("ERR: %s\n", errbuf);
125 return;
126 }
127  
128  
129 int i = 0;
130 int p_len;
131 while ((packet = pcap_next(pcap, &header)) != NULL) {
132  
133 if(discard_radiotap) {
134 int rtap_len = ((packet[3] & 0xff) << 8) | (packet[2] & 0xff);
135 packet = packet + rtap_len;
136 }
137  
138  
139 if(discard_pcap) {
140 iov[0].iov_base = (caddr_t) packet;
141 iov[0].iov_len = header.caplen;
142 msg_hdr.msg_iovlen = 1;
143 } else {
144 iov[0].iov_base = (caddr_t) &header;
145 iov[0].iov_len = sizeof(struct pcap_pkthdr);
146 iov[1].iov_base = (caddr_t) packet;
147 iov[1].iov_len = header.caplen;
148 msg_hdr.msg_iovlen = 2;
149 }
150  
151 msg_hdr.msg_name = (caddr_t) &sin;
152 msg_hdr.msg_namelen = sizeof(sin);
153 msg_hdr.msg_iov = iov;
154  
155 if(!sendmsg(sock, &msg_hdr, 0))
156 printf("ERR: %d\n", errno);
157 }
158 }
159 #endif
160  
161 void *check_parent(void *unused)
162 {
163  
164 if(pid != -1) {
165 while(1) {
166 if(kill(pid, 0) != 0) {
167 exit(EXIT_SUCCESS);
168 } else {
169 sleep(1);
170 }
171 }
172 }
173 return NULL;
174 }
175  
176 int
177 main(int argc, char **argv)
178 {
179  
180 argp_parse(&argp, argc, argv, 0, 0, 0);
181  
182 pthread_create(&p1, NULL, check_parent, (void *)NULL);
183  
184 #ifdef USE_LIBPCAP
185 if (pcap_file_name)
186 analyse_pcap_file(pcap_file_name);
187 #else
188 if (0);
189 #endif
190 else
191 fprintf(stderr, "ERR: no source selected.\n");
192  
193 exit(EXIT_SUCCESS);
194 }