Have separate callback mechanisms in file.c and capture.c; pass the
[obnox/wireshark/wip.git] / capture.c
1 /* capture.c
2  * Routines for packet capture
3  *
4  * $Id$
5  *
6  * Wireshark - Network traffic analyzer
7  * By Gerald Combs <gerald@wireshark.org>
8  * Copyright 1998 Gerald Combs
9  *
10  * This program is free software; you can redistribute it and/or
11  * modify it under the terms of the GNU General Public License
12  * as published by the Free Software Foundation; either version 2
13  * of the License, or (at your option) any later version.
14  *
15  * This program is distributed in the hope that it will be useful,
16  * but WITHOUT ANY WARRANTY; without even the implied warranty of
17  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
18  * GNU General Public License for more details.
19  *
20  * You should have received a copy of the GNU General Public License
21  * along with this program; if not, write to the Free Software
22  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
23  */
24
25 #ifdef HAVE_CONFIG_H
26 # include "config.h"
27 #endif
28
29 #ifdef HAVE_LIBPCAP
30
31 #ifdef HAVE_UNISTD_H
32 #include <unistd.h>
33 #endif
34
35 #include <stdlib.h>
36 #include <string.h>
37 #include <ctype.h>
38
39 #ifdef HAVE_FCNTL_H
40 #include <fcntl.h>
41 #endif
42
43 #ifdef HAVE_SYS_TYPES_H
44 #include <sys/types.h>
45 #endif
46
47 #ifdef HAVE_NETINET_IN_H
48 #include <netinet/in.h>
49 #endif
50
51 #ifdef HAVE_NETDB_H
52 #include <netdb.h>
53 #endif
54
55 #ifdef HAVE_ARPA_INET_H
56 #include <arpa/inet.h>
57 #endif
58
59 #ifdef HAVE_SYS_SOCKET_H
60 #include <sys/socket.h>         /* needed to define AF_ values on UNIX */
61 #endif
62
63 #ifdef HAVE_WINSOCK2_H
64 #include <winsock2.h>           /* needed to define AF_ values on Windows */
65 #endif
66
67 #ifdef NEED_INET_V6DEFS_H
68 # include "inet_v6defs.h"
69 #endif
70
71 #include <signal.h>
72 #include <errno.h>
73
74 #include <glib.h>
75
76 #include <epan/packet.h>
77 #include <epan/dfilter/dfilter.h>
78 #include "file.h"
79 #include "capture.h"
80 #include "capture_sync.h"
81 #include "capture_info.h"
82 #include "capture_ui_utils.h"
83 #include "util.h"
84 #include "capture-pcap-util.h"
85 #include "alert_box.h"
86 #include "simple_dialog.h"
87 #include <epan/prefs.h>
88
89 #ifdef _WIN32
90 #include "capture-wpcap.h"
91 #endif
92 #include "ui_util.h"
93 #include "wsutil/file_util.h"
94 #include "log.h"
95
96 typedef struct if_stat_cache_item_s {
97     char *name;
98     struct pcap_stat ps;
99 } if_stat_cache_item_t;
100
101 struct if_stat_cache_s {
102     int stat_fd;
103     int fork_child;
104     GList *cache_list;  /* List of if_stat_chache_entry_t */
105 };
106
107 /* this callback mechanism should possibly be replaced by the g_signal_...() stuff (if I only would know how :-) */
108 typedef struct {
109     capture_callback_t cb_fct;
110     gpointer user_data;
111 } capture_callback_data_t;
112
113 static GList *capture_callbacks = NULL;
114
115 static void
116 capture_callback_invoke(int event, capture_options *capture_opts)
117 {
118     capture_callback_data_t *cb;
119     GList *cb_item = capture_callbacks;
120
121     /* there should be at least one interested */
122     g_assert(cb_item != NULL);
123
124     while(cb_item != NULL) {
125         cb = cb_item->data;
126         cb->cb_fct(event, capture_opts, cb->user_data);
127         cb_item = g_list_next(cb_item);
128     }
129 }
130
131
132 void
133 capture_callback_add(capture_callback_t func, gpointer user_data)
134 {
135     capture_callback_data_t *cb;
136
137     cb = g_malloc(sizeof(capture_callback_data_t));
138     cb->cb_fct = func;
139     cb->user_data = user_data;
140
141     capture_callbacks = g_list_append(capture_callbacks, cb);
142 }
143
144 void
145 capture_callback_remove(capture_callback_t func)
146 {
147     capture_callback_data_t *cb;
148     GList *cb_item = capture_callbacks;
149
150     while(cb_item != NULL) {
151         cb = cb_item->data;
152         if(cb->cb_fct == func) {
153             capture_callbacks = g_list_remove(capture_callbacks, cb);
154             g_free(cb);
155             return;
156         }
157         cb_item = g_list_next(cb_item);
158     }
159
160     g_assert_not_reached();
161 }
162
163 /**
164  * Start a capture.
165  *
166  * @return TRUE if the capture starts successfully, FALSE otherwise.
167  */
168 gboolean
169 capture_start(capture_options *capture_opts)
170 {
171   gboolean ret;
172
173
174   /* close the currently loaded capture file */
175   cf_close(capture_opts->cf);
176
177   g_assert(capture_opts->state == CAPTURE_STOPPED);
178   capture_opts->state = CAPTURE_PREPARING;
179
180   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture Start ...");
181
182   /* try to start the capture child process */
183   ret = sync_pipe_start(capture_opts);
184   if(!ret) {
185       if(capture_opts->save_file != NULL) {
186           g_free(capture_opts->save_file);
187           capture_opts->save_file = NULL;
188       }
189
190       g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture Start failed!");
191       capture_opts->state = CAPTURE_STOPPED;
192   } else {
193       /* the capture child might not respond shortly after bringing it up */
194       /* (especially it will block, if no input coming from an input capture pipe (e.g. mkfifo) is coming in) */
195
196       /* to prevent problems, bring the main GUI into "capture mode" right after successfully */
197       /* spawn/exec the capture child, without waiting for any response from it */
198       capture_callback_invoke(capture_cb_capture_prepared, capture_opts);
199
200       if(capture_opts->show_info)
201         capture_info_open(capture_opts);
202   }
203
204   return ret;
205 }
206
207
208 void
209 capture_stop(capture_options *capture_opts)
210 {
211   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture Stop ...");
212
213   capture_callback_invoke(capture_cb_capture_stopping, capture_opts);
214
215   /* stop the capture child gracefully */
216   sync_pipe_stop(capture_opts);
217 }
218
219
220 void
221 capture_restart(capture_options *capture_opts)
222 {
223     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture Restart");
224
225     capture_opts->restart = TRUE;
226     capture_stop(capture_opts);
227 }
228
229
230 void
231 capture_kill_child(capture_options *capture_opts)
232 {
233   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_INFO, "Capture Kill");
234
235   /* kill the capture child */
236   sync_pipe_kill(capture_opts->fork_child);
237 }
238
239
240
241 /* We've succeeded a (non real-time) capture, try to read it into a new capture file */
242 static gboolean
243 capture_input_read_all(capture_options *capture_opts, gboolean is_tempfile, gboolean drops_known,
244 guint32 drops)
245 {
246   int err;
247
248
249   /* Capture succeeded; attempt to open the capture file. */
250   if (cf_open(capture_opts->cf, capture_opts->save_file, is_tempfile, &err) != CF_OK) {
251     /* We're not doing a capture any more, so we don't have a save
252        file. */
253     return FALSE;
254   }
255
256   /* Set the read filter to NULL. */
257   /* XXX - this is odd here, try to put it somewhere, where it fits better */
258   cf_set_rfcode(capture_opts->cf, NULL);
259
260   /* Get the packet-drop statistics.
261
262      XXX - there are currently no packet-drop statistics stored
263      in libpcap captures, and that's what we're reading.
264
265      At some point, we will add support in Wiretap to return
266      packet-drop statistics for capture file formats that store it,
267      and will make "cf_read()" get those statistics from Wiretap.
268      We clear the statistics (marking them as "not known") in
269      "cf_open()", and "cf_read()" will only fetch them and mark
270      them as known if Wiretap supplies them, so if we get the
271      statistics now, after calling "cf_open()" but before calling
272      "cf_read()", the values we store will be used by "cf_read()".
273
274      If a future libpcap capture file format stores the statistics,
275      we'll put them into the capture file that we write, and will
276      thus not have to set them here - "cf_read()" will get them from
277      the file and use them. */
278   if (drops_known) {
279     cf_set_drops_known(capture_opts->cf, TRUE);
280
281     /* XXX - on some systems, libpcap doesn't bother filling in
282        "ps_ifdrop" - it doesn't even set it to zero - so we don't
283        bother looking at it.
284
285        Ideally, libpcap would have an interface that gave us
286        several statistics - perhaps including various interface
287        error statistics - and would tell us which of them it
288        supplies, allowing us to display only the ones it does. */
289     cf_set_drops(capture_opts->cf, drops);
290   }
291
292   /* read in the packet data */
293   switch (cf_read(capture_opts->cf)) {
294
295   case CF_READ_OK:
296   case CF_READ_ERROR:
297     /* Just because we got an error, that doesn't mean we were unable
298        to read any of the file; we handle what we could get from the
299        file. */
300     break;
301
302   case CF_READ_ABORTED:
303     /* User wants to quit program. Exit by leaving the main loop,
304        so that any quit functions we registered get called. */
305     main_window_nested_quit();
306     return FALSE;
307   }
308
309   /* if we didn't captured even a single packet, close the file again */
310   if(cf_get_packet_count(capture_opts->cf) == 0 && !capture_opts->restart) {
311     simple_dialog(ESD_TYPE_INFO, ESD_BTN_OK,
312 "%sNo packets captured!%s\n"
313 "\n"
314 "As no data was captured, closing the %scapture file!\n"
315 "\n"
316 "\n"
317 "Help about capturing can be found at:\n"
318 "\n"
319 "       http://wiki.wireshark.org/CaptureSetup"
320 #ifdef _WIN32
321 "\n\n"
322 "Wireless (Wi-Fi/WLAN):\n"
323 "Try to switch off promiscuous mode in the Capture Options!"
324 #endif
325 "",
326     simple_dialog_primary_start(), simple_dialog_primary_end(),
327     (cf_is_tempfile(capture_opts->cf)) ? "temporary " : "");
328     cf_close(capture_opts->cf);
329   }
330   return TRUE;
331 }
332
333
334 /* capture child tells us we have a new (or the first) capture file */
335 gboolean
336 capture_input_new_file(capture_options *capture_opts, gchar *new_file)
337 {
338   gboolean is_tempfile;
339   int  err;
340
341
342   if(capture_opts->state == CAPTURE_PREPARING) {
343     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture started!");
344   }
345   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "File: \"%s\"", new_file);
346
347   g_assert(capture_opts->state == CAPTURE_PREPARING || capture_opts->state == CAPTURE_RUNNING);
348
349   /* free the old filename */
350   if(capture_opts->save_file != NULL) {
351     /* we start a new capture file, close the old one (if we had one before) */
352     /* (we can only have an open capture file in real_time_mode!) */
353     if( ((capture_file *) capture_opts->cf)->state != FILE_CLOSED) {
354         capture_callback_invoke(capture_cb_capture_update_finished, capture_opts);
355         cf_finish_tail(capture_opts->cf, &err);
356         cf_close(capture_opts->cf);
357     }
358     g_free(capture_opts->save_file);
359     is_tempfile = FALSE;
360     cf_set_tempfile(capture_opts->cf, FALSE);
361   } else {
362     /* we didn't had a save_file before, must be a tempfile */
363     is_tempfile = TRUE;
364     cf_set_tempfile(capture_opts->cf, TRUE);
365   }
366
367   /* save the new filename */
368   capture_opts->save_file = g_strdup(new_file);
369
370   /* if we are in real-time mode, open the new file now */
371   if(capture_opts->real_time_mode) {
372     /* Attempt to open the capture file and set up to read from it. */
373     switch(cf_start_tail(capture_opts->cf, capture_opts->save_file, is_tempfile, &err)) {
374     case CF_OK:
375       break;
376     case CF_ERROR:
377       /* Don't unlink (delete) the save file - leave it around,
378          for debugging purposes. */
379       g_free(capture_opts->save_file);
380       capture_opts->save_file = NULL;
381       return FALSE;
382     }
383   }
384
385   if(capture_opts->show_info) {
386     if (!capture_info_new_file(new_file))
387       return FALSE;
388   }
389
390   if(capture_opts->real_time_mode) {
391     capture_callback_invoke(capture_cb_capture_update_started, capture_opts);
392   } else {
393     capture_callback_invoke(capture_cb_capture_fixed_started, capture_opts);
394   }
395   capture_opts->state = CAPTURE_RUNNING;
396
397   return TRUE;
398 }
399
400
401 /* capture child tells us we have new packets to read */
402 void
403 capture_input_new_packets(capture_options *capture_opts, int to_read)
404 {
405   int  err;
406
407
408   g_assert(capture_opts->save_file);
409
410   if(capture_opts->real_time_mode) {
411     /* Read from the capture file the number of records the child told us it added. */
412     switch (cf_continue_tail(capture_opts->cf, to_read, &err)) {
413
414     case CF_READ_OK:
415     case CF_READ_ERROR:
416       /* Just because we got an error, that doesn't mean we were unable
417          to read any of the file; we handle what we could get from the
418          file.
419
420          XXX - abort on a read error? */
421          capture_callback_invoke(capture_cb_capture_update_continue, capture_opts);
422       break;
423
424     case CF_READ_ABORTED:
425       /* Kill the child capture process; the user wants to exit, and we
426          shouldn't just leave it running. */
427       capture_kill_child(capture_opts);
428       break;
429     }
430   } else {
431     /* increase capture file packet counter by the number or incoming packets */
432     cf_set_packet_count(capture_opts->cf,
433         cf_get_packet_count(capture_opts->cf) + to_read);
434
435     capture_callback_invoke(capture_cb_capture_fixed_continue, capture_opts);
436   }
437
438   /* update the main window, so we get events (e.g. from the stop toolbar button) */
439   main_window_update();
440
441   if(capture_opts->show_info)
442     capture_info_new_packets(to_read);
443 }
444
445
446 /* Capture child told us how many dropped packets it counted.
447  */
448 void
449 capture_input_drops(capture_options *capture_opts, int dropped)
450 {
451   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_INFO, "%d packet%s dropped", dropped, plurality(dropped, "", "s"));
452
453   g_assert(capture_opts->state == CAPTURE_RUNNING);
454
455   cf_set_drops_known(capture_opts->cf, TRUE);
456   cf_set_drops(capture_opts->cf, dropped);
457 }
458
459
460 /* Capture child told us that an error has occurred while starting/running
461    the capture.
462    The buffer we're handed has *two* null-terminated strings in it - a
463    primary message and a secondary message, one right after the other.
464    The secondary message might be a null string.
465  */
466 void
467 capture_input_error_message(capture_options *capture_opts, char *error_msg, char *secondary_error_msg)
468 {
469   gchar *safe_error_msg;
470   gchar *safe_secondary_error_msg;
471
472   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Error message from child: \"%s\", \"%s\"",
473         error_msg, secondary_error_msg);
474
475   g_assert(capture_opts->state == CAPTURE_PREPARING || capture_opts->state == CAPTURE_RUNNING);
476
477   safe_error_msg = simple_dialog_format_message(error_msg);
478   if (*secondary_error_msg != '\0') {
479     /* We have both primary and secondary messages. */
480     safe_secondary_error_msg = simple_dialog_format_message(secondary_error_msg);
481     simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "%s%s%s\n\n%s",
482                   simple_dialog_primary_start(), safe_error_msg,
483                   simple_dialog_primary_end(), safe_secondary_error_msg);
484     g_free(safe_secondary_error_msg);
485   } else {
486     /* We have only a primary message. */
487     simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "%s%s%s",
488                   simple_dialog_primary_start(), safe_error_msg,
489                   simple_dialog_primary_end());
490   }
491   g_free(safe_error_msg);
492
493   /* the capture child will close the sync_pipe if required, nothing to do for now */
494 }
495
496
497
498 /* Capture child told us that an error has occurred while parsing a
499    capture filter when starting/running the capture.
500  */
501 void
502 capture_input_cfilter_error_message(capture_options *capture_opts, char *error_message)
503 {
504   dfilter_t   *rfcode = NULL;
505   gchar *safe_cfilter = simple_dialog_format_message(capture_opts->cfilter);
506   gchar *safe_cfilter_error_msg = simple_dialog_format_message(error_message);
507
508   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture filter error message from child: \"%s\"", error_message);
509
510   g_assert(capture_opts->state == CAPTURE_PREPARING || capture_opts->state == CAPTURE_RUNNING);
511
512   /* Did the user try a display filter? */
513   if (dfilter_compile(capture_opts->cfilter, &rfcode) && rfcode != NULL) {
514     simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK,
515       "%sInvalid capture filter: \"%s\"!%s\n"
516       "\n"
517       "That string looks like a valid display filter; however, it isn't a valid\n"
518       "capture filter (%s).\n"
519       "\n"
520       "Note that display filters and capture filters don't have the same syntax,\n"
521       "so you can't use most display filter expressions as capture filters.\n"
522       "\n"
523       "See the User's Guide for a description of the capture filter syntax.",
524       simple_dialog_primary_start(), safe_cfilter,
525       simple_dialog_primary_end(), safe_cfilter_error_msg);
526       dfilter_free(rfcode);
527   } else {
528     simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK,
529       "%sInvalid capture filter: \"%s\"!%s\n"
530       "\n"
531       "That string isn't a valid capture filter (%s).\n"
532       "See the User's Guide for a description of the capture filter syntax.",
533       simple_dialog_primary_start(), safe_cfilter,
534       simple_dialog_primary_end(), safe_cfilter_error_msg);
535   }
536   g_free(safe_cfilter_error_msg);
537   g_free(safe_cfilter);
538
539   /* the capture child will close the sync_pipe if required, nothing to do for now */
540 }
541
542
543 /* capture child closed its side of the pipe, do the required cleanup */
544 void
545 capture_input_closed(capture_options *capture_opts)
546 {
547     int  err;
548     int  packet_count_save;
549
550     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture stopped!");
551     g_assert(capture_opts->state == CAPTURE_PREPARING || capture_opts->state == CAPTURE_RUNNING);
552
553     /* if we didn't started the capture, do a fake start */
554     /* (happens if we got an error message - we won't get a filename then) */
555     if(capture_opts->state == CAPTURE_PREPARING) {
556         if(capture_opts->real_time_mode) {
557             capture_callback_invoke(capture_cb_capture_update_started, capture_opts);
558         } else {
559             capture_callback_invoke(capture_cb_capture_fixed_started, capture_opts);
560         }
561     }
562
563     if(capture_opts->real_time_mode) {
564         cf_read_status_t status;
565
566         /* Read what remains of the capture file. */
567         status = cf_finish_tail(capture_opts->cf, &err);
568
569         /* XXX: If -Q (quit-after-cap) then cf->count clr'd below so save it first */
570         packet_count_save = cf_get_packet_count(capture_opts->cf);
571         /* Tell the GUI, we are not doing a capture any more.
572                    Must be done after the cf_finish_tail(), so file lengths are displayed
573                    correct. */
574         capture_callback_invoke(capture_cb_capture_update_finished, capture_opts);
575
576         /* Finish the capture. */
577         switch (status) {
578
579         case CF_READ_OK:
580             if ((packet_count_save == 0) && !capture_opts->restart) {
581                 simple_dialog(ESD_TYPE_INFO, ESD_BTN_OK,
582 "%sNo packets captured!%s\n"
583 "\n"
584 "As no data was captured, closing the %scapture file!\n"
585 "\n"
586 "\n"
587 "Help about capturing can be found at:\n"
588 "\n"
589 "       http://wiki.wireshark.org/CaptureSetup"
590 #ifdef _WIN32
591 "\n\n"
592 "Wireless (Wi-Fi/WLAN):\n"
593 "Try to switch off promiscuous mode in the Capture Options!"
594 #endif
595 "",
596               simple_dialog_primary_start(), simple_dialog_primary_end(),
597               cf_is_tempfile(capture_opts->cf) ? "temporary " : "");
598               cf_close(capture_opts->cf);
599             }
600             break;
601         case CF_READ_ERROR:
602           /* Just because we got an error, that doesn't mean we were unable
603              to read any of the file; we handle what we could get from the
604              file. */
605           break;
606
607         case CF_READ_ABORTED:
608           /* Exit by leaving the main loop, so that any quit functions
609              we registered get called. */
610           main_window_quit();
611         }
612
613     } else {
614         /* first of all, we are not doing a capture any more */
615         capture_callback_invoke(capture_cb_capture_fixed_finished, capture_opts);
616
617         /* this is a normal mode capture and if no error happened, read in the capture file data */
618         if(capture_opts->save_file != NULL) {
619             capture_input_read_all(capture_opts, cf_is_tempfile(capture_opts->cf),
620                 cf_get_drops_known(capture_opts->cf), cf_get_drops(capture_opts->cf));
621         }
622     }
623
624     if(capture_opts->show_info)
625       capture_info_close();
626
627     capture_opts->state = CAPTURE_STOPPED;
628
629     /* if we couldn't open a capture file, there's nothing more for us to do */
630     if(capture_opts->save_file == NULL) {
631         cf_close(capture_opts->cf);
632         return;
633     }
634
635     /* does the user wants to restart the current capture? */
636     if(capture_opts->restart) {
637         capture_opts->restart = FALSE;
638
639         ws_unlink(capture_opts->save_file);
640
641         /* if it was a tempfile, throw away the old filename (so it will become a tempfile again) */
642         if(cf_is_tempfile(capture_opts->cf)) {
643             g_free(capture_opts->save_file);
644             capture_opts->save_file = NULL;
645         }
646
647         /* ... and start the capture again */
648         capture_start(capture_opts);
649     } else {
650         /* We're not doing a capture any more, so we don't have a save file. */
651         g_free(capture_opts->save_file);
652         capture_opts->save_file = NULL;
653     }
654 }
655
656 /**
657  * Fetch the interface list from a child process (dumpcap).
658  *
659  * @return A GList containing if_info_t structs if successful, NULL otherwise.
660  */
661
662 /* XXX - We parse simple text output to get our interface list.  Should
663  * we use "real" data serialization instead, e.g. via XML? */
664 GList *
665 capture_interface_list(int *err, char **err_str)
666 {
667     GList     *if_list = NULL;
668     int        i, j;
669     gchar     *msg;
670     gchar    **raw_list, **if_parts, **addr_parts;
671     gchar     *name;
672     if_info_t *if_info;
673     if_addr_t *if_addr;
674
675     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture Interface List ...");
676
677     /* Try to get our interface list */
678     *err = sync_interface_list_open(&msg);
679     if (*err != 0) {
680         g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture Interface List failed!");
681         if (err_str) {
682             if (*err_str)
683                 *err_str = msg;
684             else
685                 g_free(msg);
686         } else {
687             g_free(msg);
688         }
689         return NULL;
690     }
691
692     /* Split our lines */
693 #ifdef _WIN32
694     raw_list = g_strsplit(msg, "\r\n", 0);
695 #else
696     raw_list = g_strsplit(msg, "\n", 0);
697 #endif
698     g_free(msg);
699
700     for (i = 0; raw_list[i] != NULL; i++) {
701         if_parts = g_strsplit(raw_list[i], "\t", 4);
702         if (if_parts[0] == NULL || if_parts[1] == NULL || if_parts[2] == NULL ||
703                 if_parts[3] == NULL) {
704             g_strfreev(if_parts);
705             continue;
706         }
707
708         /* Number followed by the name, e.g "1. eth0" */
709         name = strchr(if_parts[0], ' ');
710         if (name) {
711             name++;
712         } else {
713             g_strfreev(if_parts);
714             continue;
715         }
716
717         if_info = g_malloc0(sizeof(if_info_t));
718         if_info->name = g_strdup(name);
719         if (strlen(if_parts[1]) > 0)
720             if_info->description = g_strdup(if_parts[1]);
721         addr_parts = g_strsplit(if_parts[2], ",", 0);
722         for (j = 0; addr_parts[j] != NULL; j++) {
723             if_addr = g_malloc0(sizeof(if_addr_t));
724             if (inet_pton(AF_INET, addr_parts[j], &if_addr->ip_addr.ip4_addr)) {
725                 if_addr->type = AT_IPv4;
726             } else if (inet_pton(AF_INET6, addr_parts[j],
727                     &if_addr->ip_addr.ip6_addr)) {
728                 if_addr->type = AT_IPv6;
729             } else {
730                 g_free(if_addr);
731                 if_addr = NULL;
732             }
733             if (if_addr) {
734                 if_info->ip_addr = g_slist_append(if_info->ip_addr, if_addr);
735             }
736         }
737         if (strcmp(if_parts[3], "loopback") == 0)
738             if_info->loopback = TRUE;
739         g_strfreev(if_parts);
740         g_strfreev(addr_parts);
741         if_list = g_list_append(if_list, if_info);
742     }
743     g_strfreev(raw_list);
744
745     /* Check to see if we built a list */
746     if (if_list == NULL) {
747         if (err_str && *err_str)
748             *err_str = g_strdup("No interfaces found");
749         *err = NO_INTERFACES_FOUND;
750     }
751     return if_list;
752 }
753
754 /* XXX - We parse simple text output to get our interface list.  Should
755  * we use "real" data serialization instead, e.g. via XML? */
756 GList *
757 capture_pcap_linktype_list(const gchar *ifname, char **err_str)
758 {
759     GList     *linktype_list = NULL;
760     int        err, i;
761     gchar     *msg;
762     gchar    **raw_list, **lt_parts;
763     data_link_info_t *data_link_info;
764
765     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture Interface List ...");
766
767     /* Try to get our interface list */
768     err = sync_linktype_list_open(ifname, &msg);
769     if (err != 0) {
770         g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_MESSAGE, "Capture Interface List failed!");
771         if (err_str) {
772             *err_str = msg;
773         } else {
774             g_free(msg);
775         }
776         return NULL;
777     }
778
779     /* Split our lines */
780 #ifdef _WIN32
781     raw_list = g_strsplit(msg, "\r\n", 0);
782 #else
783     raw_list = g_strsplit(msg, "\n", 0);
784 #endif
785     g_free(msg);
786
787     for (i = 0; raw_list[i] != NULL; i++) {
788         /* ...and what if the interface name has a tab in it, Mr. Clever Programmer? */
789         lt_parts = g_strsplit(raw_list[i], "\t", 3);
790         if (lt_parts[0] == NULL || lt_parts[1] == NULL || lt_parts[2] == NULL) {
791             g_strfreev(lt_parts);
792             continue;
793         }
794
795         data_link_info = g_malloc(sizeof (data_link_info_t));
796         data_link_info->dlt = (int) strtol(lt_parts[0], NULL, 10);
797         data_link_info->name = g_strdup(lt_parts[1]);
798         if (strcmp(lt_parts[2], "(not supported)") != 0)
799             data_link_info->description = g_strdup(lt_parts[2]);
800         else
801             data_link_info->description = NULL;
802
803         linktype_list = g_list_append(linktype_list, data_link_info);
804     }
805     g_strfreev(raw_list);
806
807     /* Check to see if we built a list */
808     if (linktype_list == NULL) {
809         if (err_str)
810             *err_str = NULL;
811     }
812     return linktype_list;
813 }
814
815 if_stat_cache_t *
816 capture_stat_start(GList *if_list) {
817     int stat_fd, fork_child;
818     gchar *msg;
819     if_stat_cache_t *sc = NULL;
820     GList *if_entry;
821     if_info_t *if_info;
822     if_stat_cache_item_t *sc_item;
823
824     /* Fire up dumpcap. */
825     /*
826      * XXX - on systems with BPF, the number of BPF devices limits the
827      * number of devices on which you can capture simultaneously.
828      *
829      * This means that
830      *
831      *  1) this might fail if you run out of BPF devices
832      *
833      * and
834      *
835      *  2) opening every interface could leave too few BPF devices
836      *     for *other* programs.
837      *
838      * It also means the system could end up getting a lot of traffic
839      * that it has to pass through the networking stack and capture
840      * mechanism, so opening all the devices and presenting packet
841      * counts might not always be a good idea.
842      */
843      if (sync_interface_stats_open(&stat_fd, &fork_child, &msg) == 0) {
844         sc = g_malloc(sizeof(if_stat_cache_t));
845         sc->stat_fd = stat_fd;
846         sc->fork_child = fork_child;
847         sc->cache_list = NULL;
848
849         /* Initialize the cache */
850         for (if_entry = if_list; if_entry != NULL; if_entry = g_list_next(if_entry)) {
851             if_info = if_entry->data;
852             sc_item = g_malloc0(sizeof(if_stat_cache_item_t));
853             sc_item->name = g_strdup(if_info->name);
854             sc->cache_list = g_list_append(sc->cache_list, sc_item);
855         }
856     }
857     return sc;
858 }
859
860 #define MAX_STAT_LINE_LEN 500
861
862 static void
863 capture_stat_cache_update(if_stat_cache_t *sc) {
864     gchar stat_line[MAX_STAT_LINE_LEN];
865     gchar **stat_parts;
866     GList *sc_entry;
867     if_stat_cache_item_t *sc_item;
868
869     if (!sc)
870         return;
871
872     while (sync_pipe_gets_nonblock(sc->stat_fd, stat_line, MAX_STAT_LINE_LEN) > 0) {
873         g_strstrip(stat_line);
874         stat_parts = g_strsplit(stat_line, "\t", 3);
875         if (stat_parts[0] == NULL || stat_parts[1] == NULL ||
876             stat_parts[2] == NULL) {
877             g_strfreev(stat_parts);
878             continue;
879         }
880         for (sc_entry = sc->cache_list; sc_entry != NULL; sc_entry = g_list_next(sc_entry)) {
881             sc_item = sc_entry->data;
882             if (strcmp(sc_item->name, stat_parts[0]) == 0) {
883                 sc_item->ps.ps_recv = (u_int) strtoul(stat_parts[1], NULL, 10);
884                 sc_item->ps.ps_drop = (u_int) strtoul(stat_parts[2], NULL, 10);
885             }
886         }
887         g_strfreev(stat_parts);
888     }
889 }
890
891 gboolean
892 capture_stats(if_stat_cache_t *sc, char *ifname, struct pcap_stat *ps) {
893     GList *sc_entry;
894     if_stat_cache_item_t *sc_item;
895
896     if (!sc || !ifname || !ps) {
897         return FALSE;
898     }
899
900     capture_stat_cache_update(sc);
901     for (sc_entry = sc->cache_list; sc_entry != NULL; sc_entry = g_list_next(sc_entry)) {
902         sc_item = sc_entry->data;
903         if (strcmp(sc_item->name, ifname) == 0) {
904             memcpy(ps, &sc_item->ps, sizeof(struct pcap_stat));
905             return TRUE;
906         }
907     }
908     return FALSE;
909 }
910
911 void
912 capture_stat_stop(if_stat_cache_t *sc) {
913     GList *sc_entry;
914     if_stat_cache_item_t *sc_item;
915     gchar *msg;
916
917     if (!sc)
918         return;
919
920     sync_interface_stats_close(&sc->stat_fd, &sc->fork_child, &msg);
921
922     for (sc_entry = sc->cache_list; sc_entry != NULL; sc_entry = g_list_next(sc_entry)) {
923         sc_item = sc_entry->data;
924         g_free(sc_item->name);
925         g_free(sc_item);
926     }
927     g_free(sc);
928 }
929
930 #endif /* HAVE_LIBPCAP */