Handle -I in the options processing.
[obnox/wireshark/wip.git] / capture_sync.c
1 /* capture_sync.c
2  * Synchronisation between Wireshark capture parent and child instances
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 #include <glib.h>
32 #include <stdio.h>
33 #include <ctype.h>
34 #include <string.h>
35
36 #ifdef HAVE_UNISTD_H
37 #include <unistd.h>
38 #endif
39
40 #ifdef HAVE_FCNTL_H
41 #include <fcntl.h>
42 #endif
43
44 #include <signal.h>
45
46 #ifdef _WIN32
47 #include <wsutil/unicode-utils.h>
48 #endif
49
50 #ifdef HAVE_SYS_WAIT_H
51 # include <sys/wait.h>
52 #endif
53
54 #include "capture-pcap-util.h"
55
56 #ifndef _WIN32
57 /*
58  * Define various POSIX macros (and, in the case of WCOREDUMP, non-POSIX
59  * macros) on UNIX systems that don't have them.
60  */
61 #ifndef WIFEXITED
62 # define WIFEXITED(status)      (((status) & 0177) == 0)
63 #endif
64 #ifndef WIFSTOPPED
65 # define WIFSTOPPED(status)     (((status) & 0177) == 0177)
66 #endif
67 #ifndef WIFSIGNALED
68 # define WIFSIGNALED(status)    (!WIFSTOPPED(status) && !WIFEXITED(status))
69 #endif
70 #ifndef WEXITSTATUS
71 # define WEXITSTATUS(status)    ((status) >> 8)
72 #endif
73 #ifndef WTERMSIG
74 # define WTERMSIG(status)       ((status) & 0177)
75 #endif
76 #ifndef WCOREDUMP
77 # define WCOREDUMP(status)      ((status) & 0200)
78 #endif
79 #ifndef WSTOPSIG
80 # define WSTOPSIG(status)       ((status) >> 8)
81 #endif
82 #endif /* _WIN32 */
83
84 #include <epan/packet.h>
85 #include <epan/prefs.h>
86
87 #include "globals.h"
88 #include "file.h"
89 #include <epan/filesystem.h>
90 #include <epan/report_err.h>
91
92 #include "capture.h"
93 #include "capture_sync.h"
94
95 #include "sync_pipe.h"
96
97 #ifdef _WIN32
98 #include "capture-wpcap.h"
99 #endif
100 #include "ui_util.h"
101 #include <wsutil/file_util.h>
102 #include "log.h"
103
104 #ifdef _WIN32
105 #include <process.h>    /* For spawning child process */
106 #endif
107
108
109
110 #ifndef _WIN32
111 static const char *sync_pipe_signame(int);
112 #endif
113
114
115 static gboolean sync_pipe_input_cb(gint source, gpointer user_data);
116 static void sync_pipe_wait_for_child(capture_options *capture_opts);
117
118
119
120 /* Append an arg (realloc) to an argc/argv array */
121 /* (add a string pointer to a NULL-terminated array of string pointers) */
122 static const char **
123 sync_pipe_add_arg(const char **args, int *argc, const char *arg)
124 {
125   /* Grow the array; "*argc" currently contains the number of string
126      pointers, *not* counting the NULL pointer at the end, so we have
127      to add 2 in order to get the new size of the array, including the
128      new pointer and the terminating NULL pointer. */
129   args = g_realloc( (gpointer) args, (*argc + 2) * sizeof (char *));
130
131   /* Stuff the pointer into the penultimate element of the array, which
132      is the one at the index specified by "*argc". */
133   args[*argc] = arg;
134
135   /* Now bump the count. */
136   (*argc)++;
137
138   /* We overwrite the NULL pointer; put it back right after the
139      element we added. */
140   args[*argc] = NULL;
141
142   return args;
143 }
144
145
146
147 #ifdef _WIN32
148 /* Quote the argument element if necessary, so that it will get
149  * reconstructed correctly in the C runtime startup code.  Note that
150  * the unquoting algorithm in the C runtime is really weird, and
151  * rather different than what Unix shells do. See stdargv.c in the C
152  * runtime sources (in the Platform SDK, in src/crt).
153  *
154  * Stolen from GLib's protect_argv(), an internal routine that quotes
155  * string in an argument list so that they arguments will be handled
156  * correctly in the command-line string passed to CreateProcess()
157  * if that string is constructed by gluing those strings together.
158  */
159 static gchar *
160 protect_arg (const gchar *argv)
161 {
162     gchar *new_arg;
163     const gchar *p = argv;
164     gchar *q;
165     gint len = 0;
166     gboolean need_dblquotes = FALSE;
167
168     while (*p) {
169         if (*p == ' ' || *p == '\t')
170             need_dblquotes = TRUE;
171         else if (*p == '"')
172             len++;
173         else if (*p == '\\') {
174             const gchar *pp = p;
175
176             while (*pp && *pp == '\\')
177                 pp++;
178             if (*pp == '"')
179                 len++;
180         }
181         len++;
182         p++;
183     }
184
185     q = new_arg = g_malloc (len + need_dblquotes*2 + 1);
186     p = argv;
187
188     if (need_dblquotes)
189         *q++ = '"';
190
191     while (*p) {
192         if (*p == '"')
193             *q++ = '\\';
194         else if (*p == '\\') {
195             const gchar *pp = p;
196
197             while (*pp && *pp == '\\')
198                 pp++;
199             if (*pp == '"')
200                 *q++ = '\\';
201         }
202         *q++ = *p;
203         p++;
204     }
205
206     if (need_dblquotes)
207         *q++ = '"';
208     *q++ = '\0';
209
210     return new_arg;
211 }
212 #endif
213
214 /* Initialize an argument list and add dumpcap to it. */
215 static const char **
216 init_pipe_args(int *argc) {
217     const char **argv;
218     const char *progfile_dir;
219     char *exename;
220
221     progfile_dir = get_progfile_dir();
222     if (progfile_dir == NULL) {
223       return NULL;
224     }
225
226     /* Allocate the string pointer array with enough space for the
227        terminating NULL pointer. */
228     *argc = 0;
229     argv = g_malloc(sizeof (char *));
230     *argv = NULL;
231
232     /* take Wireshark's absolute program path and replace "Wireshark" with "dumpcap" */
233     exename = g_strdup_printf("%s" G_DIR_SEPARATOR_S "dumpcap", progfile_dir);
234
235     /* Make that the first argument in the argument list (argv[0]). */
236     argv = sync_pipe_add_arg(argv, argc, exename);
237
238     return argv;
239 }
240
241 #define ARGV_NUMBER_LEN 24
242 /* a new capture run: start a new dumpcap task and hand over parameters through command line */
243 gboolean
244 sync_pipe_start(capture_options *capture_opts) {
245     char ssnap[ARGV_NUMBER_LEN];
246     char sdlt[ARGV_NUMBER_LEN];
247     char scount[ARGV_NUMBER_LEN];
248     char sfilesize[ARGV_NUMBER_LEN];
249     char sfile_duration[ARGV_NUMBER_LEN];
250     char sring_num_files[ARGV_NUMBER_LEN];
251     char sautostop_files[ARGV_NUMBER_LEN];
252     char sautostop_filesize[ARGV_NUMBER_LEN];
253     char sautostop_duration[ARGV_NUMBER_LEN];
254 #ifdef HAVE_PCAP_REMOTE
255     char sauth[256];
256 #endif
257 #ifdef HAVE_PCAP_SETSAMPLING
258     char ssampling[ARGV_NUMBER_LEN];
259 #endif
260 #if defined(_WIN32) || defined(HAVE_PCAP_CREATE)
261     char buffer_size[ARGV_NUMBER_LEN];
262 #endif
263 #ifdef _WIN32
264     HANDLE sync_pipe_read;                  /* pipe used to send messages from child to parent */
265     HANDLE sync_pipe_write;                 /* pipe used to send messages from child to parent */
266     HANDLE signal_pipe;                     /* named pipe used to send messages from parent to child (currently only stop) */
267     GString *args = g_string_sized_new(200);
268     gchar *quoted_arg;
269     SECURITY_ATTRIBUTES sa;
270     STARTUPINFO si;
271     PROCESS_INFORMATION pi;
272     int i;
273     char control_id[ARGV_NUMBER_LEN];
274     gchar *signal_pipe_name;
275 #else
276     char errmsg[1024+1];
277     int sync_pipe[2];                       /* pipe used to send messages from child to parent */
278     enum PIPES { PIPE_READ, PIPE_WRITE };   /* Constants 0 and 1 for PIPE_READ and PIPE_WRITE */
279 #endif
280     int sync_pipe_read_fd;
281     int argc;
282     const char **argv;
283
284
285     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_start");
286     capture_opts_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, capture_opts);
287
288     capture_opts->fork_child = -1;
289
290     argv = init_pipe_args(&argc);
291     if (!argv) {
292         /* We don't know where to find dumpcap. */
293         report_failure("We don't know where to find dumpcap.");
294         return FALSE;
295     }
296
297     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "argv[0]: %s", argv[0]);
298
299     argv = sync_pipe_add_arg(argv, &argc, "-i");
300     argv = sync_pipe_add_arg(argv, &argc, capture_opts->iface);
301
302     if (capture_opts->has_snaplen) {
303       argv = sync_pipe_add_arg(argv, &argc, "-s");
304       g_snprintf(ssnap, ARGV_NUMBER_LEN, "%d",capture_opts->snaplen);
305       argv = sync_pipe_add_arg(argv, &argc, ssnap);
306     }
307
308     if (capture_opts->linktype != -1) {
309       argv = sync_pipe_add_arg(argv, &argc, "-y");
310       g_snprintf(sdlt, ARGV_NUMBER_LEN, "%s",linktype_val_to_name(capture_opts->linktype));
311       argv = sync_pipe_add_arg(argv, &argc, sdlt);
312     }
313
314     if(capture_opts->multi_files_on) {
315       if (capture_opts->has_autostop_filesize) {
316         argv = sync_pipe_add_arg(argv, &argc, "-b");
317         g_snprintf(sfilesize, ARGV_NUMBER_LEN, "filesize:%d",capture_opts->autostop_filesize);
318         argv = sync_pipe_add_arg(argv, &argc, sfilesize);
319       }
320
321       if (capture_opts->has_file_duration) {
322         argv = sync_pipe_add_arg(argv, &argc, "-b");
323         g_snprintf(sfile_duration, ARGV_NUMBER_LEN, "duration:%d",capture_opts->file_duration);
324         argv = sync_pipe_add_arg(argv, &argc, sfile_duration);
325       }
326
327       if (capture_opts->has_ring_num_files) {
328         argv = sync_pipe_add_arg(argv, &argc, "-b");
329         g_snprintf(sring_num_files, ARGV_NUMBER_LEN, "files:%d",capture_opts->ring_num_files);
330         argv = sync_pipe_add_arg(argv, &argc, sring_num_files);
331       }
332
333       if (capture_opts->has_autostop_files) {
334         argv = sync_pipe_add_arg(argv, &argc, "-a");
335         g_snprintf(sautostop_files, ARGV_NUMBER_LEN, "files:%d",capture_opts->autostop_files);
336         argv = sync_pipe_add_arg(argv, &argc, sautostop_files);
337       }
338     } else {
339         if (capture_opts->has_autostop_filesize) {
340           argv = sync_pipe_add_arg(argv, &argc, "-a");
341           g_snprintf(sautostop_filesize, ARGV_NUMBER_LEN, "filesize:%d",capture_opts->autostop_filesize);
342           argv = sync_pipe_add_arg(argv, &argc, sautostop_filesize);
343         }
344     }
345
346     if (capture_opts->has_autostop_packets) {
347       argv = sync_pipe_add_arg(argv, &argc, "-c");
348       g_snprintf(scount, ARGV_NUMBER_LEN, "%d",capture_opts->autostop_packets);
349       argv = sync_pipe_add_arg(argv, &argc, scount);
350     }
351
352     if (capture_opts->has_autostop_duration) {
353       argv = sync_pipe_add_arg(argv, &argc, "-a");
354       g_snprintf(sautostop_duration, ARGV_NUMBER_LEN, "duration:%d",capture_opts->autostop_duration);
355       argv = sync_pipe_add_arg(argv, &argc, sautostop_duration);
356     }
357
358     if (!capture_opts->promisc_mode)
359       argv = sync_pipe_add_arg(argv, &argc, "-p");
360     if (capture_opts->use_pcapng)
361       argv = sync_pipe_add_arg(argv, &argc, "-n");
362 #ifdef HAVE_PCAP_REMOTE
363     if (capture_opts->datatx_udp)
364       argv = sync_pipe_add_arg(argv, &argc, "-u");
365
366     if (!capture_opts->nocap_rpcap)
367       argv = sync_pipe_add_arg(argv, &argc, "-r");
368
369     if (capture_opts->auth_type == CAPTURE_AUTH_PWD)
370     {
371         argv = sync_pipe_add_arg(argv, &argc, "-A");
372         g_snprintf(sauth, sizeof(sauth), "%s:%s", capture_opts->auth_username,
373                    capture_opts->auth_password);
374         argv = sync_pipe_add_arg(argv, &argc, sauth);
375     }
376 #endif
377 #ifdef HAVE_PCAP_SETSAMPLING
378     if (capture_opts->sampling_method != CAPTURE_SAMP_NONE)
379     {
380         argv = sync_pipe_add_arg(argv, &argc, "-m");
381         g_snprintf(ssampling, ARGV_NUMBER_LEN, "%s:%d",
382              capture_opts->sampling_method == CAPTURE_SAMP_BY_COUNT ? "count" :
383              capture_opts->sampling_method == CAPTURE_SAMP_BY_TIMER ? "timer" :
384              "undef",
385              capture_opts->sampling_param);
386         argv = sync_pipe_add_arg(argv, &argc, ssampling);
387     }
388 #endif
389
390     /* dumpcap should be running in capture child mode (hidden feature) */
391 #ifndef DEBUG_CHILD
392     argv = sync_pipe_add_arg(argv, &argc, "-Z");
393 #ifdef _WIN32
394     g_snprintf(control_id, ARGV_NUMBER_LEN, "%d", GetCurrentProcessId());
395     argv = sync_pipe_add_arg(argv, &argc, control_id);
396 #else
397     argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
398 #endif
399 #endif
400
401 #if defined(_WIN32) || defined(HAVE_PCAP_CREATE)
402     argv = sync_pipe_add_arg(argv, &argc, "-B");
403 #ifdef HAVE_PCAP_REMOTE
404     if (capture_opts->src_type == CAPTURE_IFREMOTE)
405       /* No buffer size when using remote interfaces */
406       g_snprintf(buffer_size, ARGV_NUMBER_LEN, "%d", 1);
407     else
408 #endif
409     g_snprintf(buffer_size, ARGV_NUMBER_LEN, "%d",capture_opts->buffer_size);
410     argv = sync_pipe_add_arg(argv, &argc, buffer_size);
411 #endif
412
413     if (capture_opts->cfilter != NULL && strlen(capture_opts->cfilter) != 0) {
414       argv = sync_pipe_add_arg(argv, &argc, "-f");
415       argv = sync_pipe_add_arg(argv, &argc, capture_opts->cfilter);
416     }
417
418     if(capture_opts->save_file) {
419       argv = sync_pipe_add_arg(argv, &argc, "-w");
420       argv = sync_pipe_add_arg(argv, &argc, capture_opts->save_file);
421     }
422
423 #ifdef _WIN32
424     /* init SECURITY_ATTRIBUTES */
425     sa.nLength = sizeof(SECURITY_ATTRIBUTES);
426     sa.bInheritHandle = TRUE;
427     sa.lpSecurityDescriptor = NULL;
428
429     /* Create a pipe for the child process */
430     /* (increase this value if you have trouble while fast capture file switches) */
431     if (! CreatePipe(&sync_pipe_read, &sync_pipe_write, &sa, 5120)) {
432       /* Couldn't create the pipe between parent and child. */
433       report_failure("Couldn't create sync pipe: %s", strerror(errno));
434       g_free( (gpointer) argv[0]);
435       g_free( (gpointer) argv);
436       return FALSE;
437     }
438
439     /* Create the signal pipe */
440     signal_pipe_name = g_strdup_printf(SIGNAL_PIPE_FORMAT, control_id);
441     signal_pipe = CreateNamedPipe(utf_8to16(signal_pipe_name),
442       PIPE_ACCESS_OUTBOUND, PIPE_TYPE_BYTE, 1, 65535, 65535, 0, NULL);
443     g_free(signal_pipe_name);
444
445     if (signal_pipe == INVALID_HANDLE_VALUE) {
446       /* Couldn't create the signal pipe between parent and child. */
447       report_failure("Couldn't create signal pipe: %s", strerror(errno));
448       g_free( (gpointer) argv[0]);
449       g_free( (gpointer) argv);
450       return FALSE;
451     }
452
453     /* init STARTUPINFO */
454     memset(&si, 0, sizeof(si));
455     si.cb           = sizeof(si);
456 #ifdef DEBUG_CHILD
457     si.dwFlags = STARTF_USESHOWWINDOW;
458     si.wShowWindow  = SW_SHOW;
459 #else
460     si.dwFlags = STARTF_USESTDHANDLES|STARTF_USESHOWWINDOW;
461     si.wShowWindow  = SW_HIDE;  /* this hides the console window */
462     si.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
463     si.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE);
464     si.hStdError = sync_pipe_write;
465     /*si.hStdError = (HANDLE) _get_osfhandle(2);*/
466 #endif
467
468     /* convert args array into a single string */
469     /* XXX - could change sync_pipe_add_arg() instead */
470     /* there is a drawback here: the length is internally limited to 1024 bytes */
471     for(i=0; argv[i] != 0; i++) {
472         if(i != 0) g_string_append_c(args, ' ');    /* don't prepend a space before the path!!! */
473         quoted_arg = protect_arg(argv[i]);
474         g_string_append(args, quoted_arg);
475         g_free(quoted_arg);
476     }
477
478     /* call dumpcap */
479     if(!CreateProcess(NULL, utf_8to16(args->str), NULL, NULL, TRUE,
480                       CREATE_NEW_CONSOLE, NULL, NULL, &si, &pi)) {
481       report_failure("Couldn't run %s in child process: error %u",
482                      args->str, GetLastError());
483       CloseHandle(sync_pipe_read);
484       CloseHandle(sync_pipe_write);
485       g_free( (gpointer) argv[0]);
486       g_free( (gpointer) argv);
487       return FALSE;
488     }
489     capture_opts->fork_child = (int) pi.hProcess;
490     g_string_free(args, TRUE);
491
492     /* associate the operating system filehandle to a C run-time file handle */
493     /* (good file handle infos at: http://www.flounder.com/handles.htm) */
494     sync_pipe_read_fd = _open_osfhandle( (long) sync_pipe_read, _O_BINARY);
495
496     /* associate the operating system filehandle to a C run-time file handle */
497     capture_opts->signal_pipe_write_fd = _open_osfhandle( (long) signal_pipe, _O_BINARY);
498
499 #else /* _WIN32 */
500     if (pipe(sync_pipe) < 0) {
501       /* Couldn't create the pipe between parent and child. */
502       report_failure("Couldn't create sync pipe: %s", strerror(errno));
503       g_free( (gpointer) argv[0]);
504       g_free(argv);
505       return FALSE;
506     }
507
508     if ((capture_opts->fork_child = fork()) == 0) {
509       /*
510        * Child process - run dumpcap with the right arguments to make
511        * it just capture with the specified capture parameters
512        */
513       dup2(sync_pipe[PIPE_WRITE], 2);
514       ws_close(sync_pipe[PIPE_READ]);
515       execv(argv[0], (gpointer)argv);
516       g_snprintf(errmsg, sizeof errmsg, "Couldn't run %s in child process: %s",
517                 argv[0], strerror(errno));
518       sync_pipe_errmsg_to_parent(2, errmsg, "");
519
520       /* Exit with "_exit()", so that we don't close the connection
521          to the X server (and cause stuff buffered up by our parent but
522          not yet sent to be sent, as that stuff should only be sent by
523          our parent).  We've sent an error message to the parent, so
524          we exit with an exit status of 1 (any exit status other than
525          0 or 1 will cause an additional message to report that exit
526          status, over and above the error message we sent to the parent). */
527       _exit(1);
528     }
529
530     sync_pipe_read_fd = sync_pipe[PIPE_READ];
531 #endif
532
533     g_free( (gpointer) argv[0]);  /* exename */
534
535     /* Parent process - read messages from the child process over the
536        sync pipe. */
537     g_free( (gpointer) argv);   /* free up arg array */
538
539     /* Close the write side of the pipe, so that only the child has it
540        open, and thus it completely closes, and thus returns to us
541        an EOF indication, if the child closes it (either deliberately
542        or by exiting abnormally). */
543 #ifdef _WIN32
544     CloseHandle(sync_pipe_write);
545 #else
546     ws_close(sync_pipe[PIPE_WRITE]);
547 #endif
548
549     if (capture_opts->fork_child == -1) {
550       /* We couldn't even create the child process. */
551       report_failure("Couldn't create child process: %s", strerror(errno));
552       ws_close(sync_pipe_read_fd);
553 #ifdef _WIN32
554       ws_close(capture_opts->signal_pipe_write_fd);
555 #endif
556       return FALSE;
557     }
558
559     /* we might wait for a moment till child is ready, so update screen now */
560     main_window_update();
561
562     /* We were able to set up to read the capture file;
563        arrange that our callback be called whenever it's possible
564        to read from the sync pipe, so that it's called when
565        the child process wants to tell us something. */
566
567     /* we have a running capture, now wait for the real capture filename */
568     pipe_input_set_handler(sync_pipe_read_fd, (gpointer) capture_opts,
569         &capture_opts->fork_child, sync_pipe_input_cb);
570
571     return TRUE;
572 }
573
574 /*
575  * Open a pipe to dumpcap with the supplied arguments.  On success, *msg
576  * is unchanged and 0 is returned; read_fd and fork_child point to the
577  * pipe's file descriptor and child PID/handle, respectively.  On failure,
578  * *msg points to an error message for the failure, and -1 is returned.
579  * In the latter case, *msg must be freed with g_free().
580  */
581 /* XXX - This duplicates a lot of code in sync_pipe_start() */
582 #define PIPE_BUF_SIZE 5120
583 static int
584 sync_pipe_open_command(const char** argv, int *read_fd, int *fork_child, gchar **msg) {
585 #ifdef _WIN32
586     HANDLE sync_pipe_read;                  /* pipe used to send messages from child to parent */
587     HANDLE sync_pipe_write;                 /* pipe used to send messages from parent to child */
588     GString *args = g_string_sized_new(200);
589     gchar *quoted_arg;
590     SECURITY_ATTRIBUTES sa;
591     STARTUPINFO si;
592     PROCESS_INFORMATION pi;
593     int i;
594 #else
595     char errmsg[1024+1];
596     int sync_pipe[2];                       /* pipe used to send messages from child to parent */
597     enum PIPES { PIPE_READ, PIPE_WRITE };   /* Constants 0 and 1 for PIPE_READ and PIPE_WRITE */
598 #endif
599
600     *fork_child = -1;
601     *read_fd = -1;
602     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_run_command");
603
604     if (!msg) {
605         /* We can't return anything */
606 #ifdef _WIN32
607         g_string_free(args, TRUE);
608 #endif
609         return -1;
610     }
611
612 #ifdef _WIN32
613     /* init SECURITY_ATTRIBUTES */
614     sa.nLength = sizeof(SECURITY_ATTRIBUTES);
615     sa.bInheritHandle = TRUE;
616     sa.lpSecurityDescriptor = NULL;
617
618     /* Create a pipe for the child process */
619     /* (increase this value if you have trouble while fast capture file switches) */
620     if (! CreatePipe(&sync_pipe_read, &sync_pipe_write, &sa, 5120)) {
621         /* Couldn't create the pipe between parent and child. */
622         *msg = g_strdup_printf("Couldn't create sync pipe: %s", strerror(errno));
623         g_free( (gpointer) argv[0]);
624         g_free( (gpointer) argv);
625         return -1;
626     }
627
628     /* init STARTUPINFO */
629     memset(&si, 0, sizeof(si));
630     si.cb           = sizeof(si);
631 #ifdef DEBUG_CHILD
632     si.dwFlags = STARTF_USESHOWWINDOW;
633     si.wShowWindow  = SW_SHOW;
634 #else
635     si.dwFlags = STARTF_USESTDHANDLES|STARTF_USESHOWWINDOW;
636     si.wShowWindow  = SW_HIDE;  /* this hides the console window */
637     si.hStdInput = NULL;
638     si.hStdOutput = sync_pipe_write;
639     si.hStdError = sync_pipe_write;
640     /*si.hStdError = (HANDLE) _get_osfhandle(2);*/
641 #endif
642
643     /* convert args array into a single string */
644     /* XXX - could change sync_pipe_add_arg() instead */
645     /* there is a drawback here: the length is internally limited to 1024 bytes */
646     for(i=0; argv[i] != 0; i++) {
647         if(i != 0) g_string_append_c(args, ' ');    /* don't prepend a space before the path!!! */
648         quoted_arg = protect_arg(argv[i]);
649         g_string_append(args, quoted_arg);
650         g_free(quoted_arg);
651     }
652
653     /* call dumpcap */
654     if(!CreateProcess(NULL, utf_8to16(args->str), NULL, NULL, TRUE,
655                       CREATE_NEW_CONSOLE, NULL, NULL, &si, &pi)) {
656         *msg = g_strdup_printf("Couldn't run %s in child process: error %u",
657                         args->str, GetLastError());
658         CloseHandle(sync_pipe_read);
659         CloseHandle(sync_pipe_write);
660         g_free( (gpointer) argv[0]);
661         g_free( (gpointer) argv);
662         return -1;
663     }
664     *fork_child = (int) pi.hProcess;
665     g_string_free(args, TRUE);
666
667     /* associate the operating system filehandle to a C run-time file handle */
668     /* (good file handle infos at: http://www.flounder.com/handles.htm) */
669     *read_fd = _open_osfhandle( (long) sync_pipe_read, _O_BINARY);
670
671 #else /* _WIN32 */
672     if (pipe(sync_pipe) < 0) {
673         /* Couldn't create the pipe between parent and child. */
674         *msg = g_strdup_printf("Couldn't create sync pipe: %s", strerror(errno));
675         g_free( (gpointer) argv[0]);
676         g_free(argv);
677         return -1;
678     }
679
680     if ((*fork_child = fork()) == 0) {
681         /*
682          * Child process - run dumpcap with the right arguments to make
683          * it just capture with the specified capture parameters
684          */
685         dup2(sync_pipe[PIPE_WRITE], 1);
686         ws_close(sync_pipe[PIPE_READ]);
687         execv(argv[0], (gpointer)argv);
688         g_snprintf(errmsg, sizeof errmsg, "Couldn't run %s in child process: %s",
689                    argv[0], strerror(errno));
690         sync_pipe_errmsg_to_parent(1, errmsg, "");
691
692         /* Exit with "_exit()", so that we don't close the connection
693            to the X server (and cause stuff buffered up by our parent but
694            not yet sent to be sent, as that stuff should only be sent by
695            our parent).  We've sent an error message to the parent, so
696            we exit with an exit status of 1 (any exit status other than
697            0 or 1 will cause an additional message to report that exit
698            status, over and above the error message we sent to the parent). */
699         _exit(1);
700     }
701
702     *read_fd = sync_pipe[PIPE_READ];
703 #endif
704
705     g_free( (gpointer) argv[0]);  /* exename */
706
707     /* Parent process - read messages from the child process over the
708        sync pipe. */
709     g_free( (gpointer) argv);   /* free up arg array */
710
711     /* Close the write side of the pipe, so that only the child has it
712        open, and thus it completely closes, and thus returns to us
713        an EOF indication, if the child closes it (either deliberately
714        or by exiting abnormally). */
715 #ifdef _WIN32
716     CloseHandle(sync_pipe_write);
717 #else
718     ws_close(sync_pipe[PIPE_WRITE]);
719 #endif
720
721     if (*fork_child == -1) {
722         /* We couldn't even create the child process. */
723         *msg = g_strdup_printf("Couldn't create child process: %s", strerror(errno));
724         ws_close(*read_fd);
725         return -1;
726     }
727
728     /* we might wait for a moment till child is ready, so update screen now */
729     main_window_update();
730     return 0;
731 }
732
733 /*
734  * Wait for dumpcap to finish.  On success, *msg is unchanged, and 0 is
735  * returned.  On failure, *msg points to an error message for the
736  * failure, and -1 is returned.  In the latter case, *msg must be
737  * freed with g_free().
738  */
739 static int
740 #ifdef _WIN32
741 sync_pipe_close_command(int *read_fd, int *fork_child, gchar **msg) {
742 #else
743 sync_pipe_close_command(int *read_fd, gchar **msg) {
744 #endif
745     int fork_child_status;
746
747     ws_close(*read_fd);
748
749     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_close_command: wait till child closed");
750
751 #ifdef _WIN32
752     /* XXX - Should we signal the child somehow? */
753     sync_pipe_kill(*fork_child);
754     if (_cwait(&fork_child_status, *fork_child, _WAIT_CHILD) == -1) {
755         *msg = g_strdup_printf("Child capture process stopped unexpectedly "
756             "(errno:%u)", errno);
757         return -1;
758     }
759 #else
760     if (wait(&fork_child_status) != -1) {
761         if (WIFEXITED(fork_child_status)) {
762             /* The child exited. */
763             fork_child_status = WEXITSTATUS(fork_child_status);
764         } else {
765             if (WIFSTOPPED(fork_child_status)) {
766                 /* It stopped, rather than exiting.  "Should not happen." */
767                 *msg = g_strdup_printf("Child capture process stopped: %s",
768                     sync_pipe_signame(WSTOPSIG(fork_child_status)));
769             } else if (WIFSIGNALED(fork_child_status)) {
770                 /* It died with a signal. */
771                 *msg = g_strdup_printf("Child capture process died: %s%s",
772                     sync_pipe_signame(WTERMSIG(fork_child_status)),
773                     WCOREDUMP(fork_child_status) ? " - core dumped" : "");
774             } else {
775                 /* What?  It had to either have exited, or stopped, or died with
776                    a signal; what happened here? */
777                 *msg = g_strdup_printf("Child capture process died: wait status %#o",
778                     fork_child_status);
779             }
780             return -1;
781         }
782     } else {
783       *msg = g_strdup_printf("Child capture process stopped unexpectedly "
784         "(errno:%u)", errno);
785       return -1;
786     }
787 #endif
788     return 0;
789 }
790
791 /*
792  * Run dumpcap with the supplied arguments.  On success, *msg points to
793  * a buffer containing the dumpcap output, and 0 is returned.  On failure,
794  * *msg points to an error message, and -1 is returned.  In either case,
795  * *msg must be freed with g_free().
796  *
797  * XXX - this doesn't check the exit status of dumpcap if it can be
798  * started and its return status could be fetched.
799  */
800 /* XXX - This duplicates a lot of code in sync_pipe_start() */
801 #define PIPE_BUF_SIZE 5120
802 static int
803 sync_pipe_run_command(const char** argv, gchar **msg) {
804     int sync_pipe_read_fd, fork_child, ret;
805     gchar buf[PIPE_BUF_SIZE+1];
806     GString *msg_buf = NULL;
807     int count;
808
809     ret = sync_pipe_open_command(argv, &sync_pipe_read_fd, &fork_child, msg);
810
811     if (ret)
812         return ret;
813
814     /* We were able to set up to read dumpcap's output.  Do so. */
815     msg_buf = g_string_new("");
816     while ((count = ws_read(sync_pipe_read_fd, buf, PIPE_BUF_SIZE)) > 0) {
817         buf[count] = '\0';
818         g_string_append(msg_buf, buf);
819     }
820
821 #ifdef _WIN32
822     ret = sync_pipe_close_command(&sync_pipe_read_fd, &fork_child, msg);
823 #else
824     ret = sync_pipe_close_command(&sync_pipe_read_fd, msg);
825 #endif
826
827     if (ret) {
828         g_string_free(msg_buf, TRUE);
829         return ret;
830     }
831
832     *msg = msg_buf->str;
833     g_string_free(msg_buf, FALSE);
834     return 0;
835 }
836
837 /*
838  * Get an interface list using dumpcap.  On success, *msg points to
839  * a buffer containing the dumpcap output, and 0 is returned.  On failure,
840  * *msg points to an error message, and -1 is returned.  In either case,
841  * msg must be freed with g_free().
842  */
843 int
844 sync_interface_list_open(gchar **msg) {
845     int argc;
846     const char **argv;
847
848     if (!msg) {
849         /* We can't return anything */
850         return -1;
851     }
852
853     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_interface_list_open");
854
855     argv = init_pipe_args(&argc);
856
857     if (!argv) {
858         *msg = g_strdup_printf("We don't know where to find dumpcap.");
859         return -1;
860     }
861
862     /* Ask for the interface list */
863     argv = sync_pipe_add_arg(argv, &argc, "-D");
864     argv = sync_pipe_add_arg(argv, &argc, "-M");
865
866 #if 0
867     /* dumpcap should be running in capture child mode (hidden feature)                   */
868     /* XXX: Actually: don't run dumpcap in capture_child_mode.                            */
869     /*     Instead run dumpcap in 'normal' mode so that dumpcap err msgs are sent to      */
870     /*     stderr in normal format and are then sent to whereever our stderr goes.        */
871     /*     Note: Using 'dumpcap -D -M -Z' (capture_child mode) changes only the format of */
872     /*           dumpcap err msgs. That is: dumpcap in capture_child mode outputs err     */
873     /*           msgs to stderr in a special type/len/string format which would then      */
874     /*           currently be sent as is to stderr resulting in garbled output.           */
875     /*     ToDo: Revise this code to be similar to sync_pipe_start so that 'dumpcap -Z'   */
876     /*     special format error messages to stderr are captured and returned to caller    */
877     /*     (eg: so can be processed and displayed in a pop-up box).                       */
878 #ifndef DEBUG_CHILD
879     argv = sync_pipe_add_arg(argv, &argc, "-Z");
880     argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
881 #endif
882 #endif
883
884     return sync_pipe_run_command(argv, msg);
885 }
886
887 /*
888  * Get an linktype list using dumpcap.  On success, *msg points to
889  * a buffer containing the dumpcap output, and 0 is returned.  On failure,
890  * *msg points to an error message, and -1 is returned.  In either case,
891  * *msg must be freed with g_free().
892  */
893 int
894 sync_linktype_list_open(const gchar *ifname, gchar **msg) {
895     int argc;
896     const char **argv;
897
898     if (!msg) {
899         /* We can't return anything */
900         return -1;
901     }
902
903     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_linktype_list_open");
904
905     argv = init_pipe_args(&argc);
906
907     if (!argv) {
908         *msg = g_strdup_printf("We don't know where to find dumpcap.");
909         return -1;
910     }
911
912     /* Ask for the linktype list */
913     argv = sync_pipe_add_arg(argv, &argc, "-i");
914     argv = sync_pipe_add_arg(argv, &argc, ifname);
915     argv = sync_pipe_add_arg(argv, &argc, "-L");
916     argv = sync_pipe_add_arg(argv, &argc, "-M");
917
918 #if 0
919     /* dumpcap should be running in capture child mode (hidden feature)                   */
920     /* XXX: Actually: don't run dumpcap in capture_child_mode.                            */
921     /*     Instead run dumpcap in 'normal' mode so that dumpcap err msgs are sent to      */
922     /*     stderr in normal format and are then sent to whereever our stderr goes.        */
923     /*     Note: Using 'dumpcap -L -M -Z' (capture_child mode) changes only the format of */
924     /*           dumpcap err msgs. That is: dumpcap in capture_child mode outputs err     */
925     /*           msgs to stderr in a special type/len/string format which would then      */
926     /*           currently be sent as is to stderr resulting in garbled output.           */
927     /*     ToDo: Revise this code to be similar to sync_pipe_start so that 'dumpcap -Z'   */
928     /*     special format error messages to stderr are captured and returned to caller    */
929     /*     (eg: so can be processed and displayed in a pop-up box).                       */
930 #ifndef DEBUG_CHILD
931     argv = sync_pipe_add_arg(argv, &argc, "-Z");
932     argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
933 #endif
934 #endif
935     return sync_pipe_run_command(argv, msg);
936 }
937
938 /*
939  * Start getting interface statistics using dumpcap.  On success, read_fd
940  * contains the file descriptor for the pipe's stdout, *msg is unchanged,
941  * and zero is returned.  On failure, *msg will point to an error message
942  * that must be g_free()d, and -1 will be returned.
943  */
944 int
945 sync_interface_stats_open(int *read_fd, int *fork_child, gchar **msg) {
946     int argc;
947     const char **argv;
948
949     if (!msg) {
950         /* We can't return anything */
951         return -1;
952     }
953
954     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_interface_stats_open");
955
956     argv = init_pipe_args(&argc);
957
958     if (!argv) {
959         *msg = g_strdup_printf("We don't know where to find dumpcap.");
960         return -1;
961     }
962
963     /* Ask for the interface statistics */
964     argv = sync_pipe_add_arg(argv, &argc, "-S");
965     argv = sync_pipe_add_arg(argv, &argc, "-M");
966
967 #if 0
968     /* dumpcap should be running in capture child mode (hidden feature)                   */
969     /* XXX: Actually: don't run dumpcap in capture_child_mode.                            */
970     /*     Instead run dumpcap in 'normal' mode so that dumpcap err msgs are sent to      */
971     /*     stderr in normal format and are then sent to whereever our stderr goes.        */
972     /*     Note: Using 'dumpcap -S -M -Z' (capture_child mode) changes only the format of */
973     /*           dumpcap err msgs. That is: dumpcap in capture_child mode outputs err     */
974     /*           msgs to stderr in a special type/len/string format which would then      */
975     /*           currently be sent as is to stderr resulting in garbled output.           */
976     /*     ToDo: Revise this code to be similar to sync_pipe_start so that 'dumpcap -Z'   */
977     /*     special format error messages to stderr are captured and returned to caller    */
978     /*     (eg: so can be processed and displayed in a pop-up box).                       */
979 #ifndef DEBUG_CHILD
980     argv = sync_pipe_add_arg(argv, &argc, "-Z");
981     argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
982 #endif
983 #endif
984     return sync_pipe_open_command(argv, read_fd, fork_child, msg);
985 }
986
987 /* Close down the stats process */
988 int
989 sync_interface_stats_close(int *read_fd, int *fork_child
990 #ifndef _WIN32
991 _U_
992 #endif
993 , gchar **msg) {
994 #ifdef _WIN32
995     return sync_pipe_close_command(read_fd, fork_child, msg);
996 #else
997     return sync_pipe_close_command(read_fd, msg);
998 #endif
999 }
1000
1001 /* read a number of bytes from a pipe */
1002 /* (blocks until enough bytes read or an error occurs) */
1003 static int
1004 pipe_read_bytes(int pipe_fd, char *bytes, int required) {
1005     int newly;
1006     int offset = 0;
1007
1008     while(required) {
1009         newly = read(pipe_fd, &bytes[offset], required);
1010         if (newly == 0) {
1011             /* EOF */
1012             g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1013                   "read from pipe %d: EOF (capture closed?)", pipe_fd);
1014             return offset;
1015         }
1016         if (newly < 0) {
1017             /* error */
1018             g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1019                   "read from pipe %d: error(%u): %s", pipe_fd, errno, strerror(errno));
1020             return newly;
1021         }
1022
1023         required -= newly;
1024         offset += newly;
1025     }
1026
1027     return offset;
1028 }
1029
1030 static gboolean pipe_data_available(int pipe_fd) {
1031 #ifdef _WIN32 /* PeekNamedPipe */
1032     HANDLE hPipe = (HANDLE) _get_osfhandle(pipe_fd);
1033     DWORD bytes_avail;
1034
1035     if (hPipe == INVALID_HANDLE_VALUE)
1036         return FALSE;
1037
1038     if (! PeekNamedPipe(hPipe, NULL, 0, NULL, &bytes_avail, NULL))
1039         return FALSE;
1040
1041     if (bytes_avail > 0)
1042         return TRUE;
1043     return FALSE;
1044 #else /* select */
1045     fd_set rfds;
1046     struct timeval timeout;
1047
1048     FD_ZERO(&rfds);
1049     FD_SET(pipe_fd, &rfds);
1050     timeout.tv_sec = 0;
1051     timeout.tv_usec = 0;
1052
1053     if (select(pipe_fd+1, &rfds, NULL, NULL, &timeout) > 0)
1054         return TRUE;
1055
1056     return FALSE;
1057 #endif
1058 }
1059
1060 /* Read a line from a pipe, similar to fgets */
1061 int
1062 sync_pipe_gets_nonblock(int pipe_fd, char *bytes, int max) {
1063     int newly;
1064     int offset = -1;
1065
1066     while(offset < max - 1) {
1067         offset++;
1068         if (! pipe_data_available(pipe_fd))
1069             break;
1070         newly = read(pipe_fd, &bytes[offset], 1);
1071         if (newly == 0) {
1072             /* EOF - not necessarily an error */
1073             break;
1074         } else if (newly < 0) {
1075             /* error */
1076             g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1077                   "read from pipe %d: error(%u): %s", pipe_fd, errno, strerror(errno));
1078             return newly;
1079         } else if (bytes[offset] == '\n') {
1080             break;
1081         }
1082     }
1083
1084     if (offset >= 0)
1085         bytes[offset] = '\0';
1086
1087     return offset;
1088 }
1089
1090
1091 /* convert header values (indicator and 4-byte length) */
1092 static void
1093 pipe_convert_header(const guchar *header, int header_len, char *indicator, int *block_len) {
1094
1095     g_assert(header_len == 4);
1096
1097     /* convert header values */
1098     *indicator = header[0];
1099     *block_len = header[1]<<16 | header[2]<<8 | header[3];
1100 }
1101
1102 /* read a message from the sending pipe in the standard format
1103    (1-byte message indicator, 3-byte message length (excluding length
1104    and indicator field), and the rest is the message) */
1105 static int
1106 pipe_read_block(int pipe_fd, char *indicator, int len, char *msg) {
1107     int required;
1108     int newly;
1109     guchar header[4];
1110
1111
1112     /* read header (indicator and 3-byte length) */
1113     newly = pipe_read_bytes(pipe_fd, header, 4);
1114     if(newly != 4) {
1115         g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1116               "read %d failed to read header: %u", pipe_fd, newly);
1117         return -1;
1118     }
1119
1120     /* convert header values */
1121     pipe_convert_header(header, 4, indicator, &required);
1122
1123     /* only indicator with no value? */
1124     if(required == 0) {
1125         g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1126               "read %d indicator: %c empty value", pipe_fd, *indicator);
1127         return 4;
1128     }
1129
1130     /* does the data fit into the given buffer? */
1131     if(required > len) {
1132         g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1133               "read %d length error, required %d > len %d, indicator: %u",
1134               pipe_fd, required, len, *indicator);
1135
1136         /* we have a problem here, try to read some more bytes from the pipe to debug where the problem really is */
1137         memcpy(msg, header, sizeof(header));
1138         newly = read(pipe_fd, &msg[sizeof(header)], len-sizeof(header));
1139         g_warning("Unknown message from dumpcap, try to show it as a string: %s", msg);
1140         return -1;
1141     }
1142     len = required;
1143
1144     /* read the actual block data */
1145     newly = pipe_read_bytes(pipe_fd, msg, required);
1146     if(newly != required) {
1147         g_warning("Unknown message from dumpcap, try to show it as a string: %s", msg);
1148         return -1;
1149     }
1150
1151     /* XXX If message is "2part", the msg probably won't be sent to debug log correctly */
1152     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1153           "read %d ok indicator: %c len: %u msg: %s", pipe_fd, *indicator,
1154           len, msg);
1155     return newly + 4;
1156 }
1157
1158
1159 /* There's stuff to read from the sync pipe, meaning the child has sent
1160    us a message, or the sync pipe has closed, meaning the child has
1161    closed it (perhaps because it exited). */
1162 static gboolean
1163 sync_pipe_input_cb(gint source, gpointer user_data)
1164 {
1165   capture_options *capture_opts = (capture_options *)user_data;
1166   char buffer[SP_MAX_MSG_LEN+1];
1167   int  nread;
1168   char indicator;
1169   int  primary_len;
1170   char * primary_msg;
1171   int  secondary_len;
1172   char * secondary_msg;
1173
1174
1175   nread = pipe_read_block(source, &indicator, SP_MAX_MSG_LEN, buffer);
1176   if(nread <= 0) {
1177     if (nread == 0)
1178       g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1179             "sync_pipe_input_cb: child has closed sync_pipe");
1180     else
1181       g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1182             "sync_pipe_input_cb: error reading from sync pipe");
1183
1184     /* The child has closed the sync pipe, meaning it's not going to be
1185        capturing any more packets.  Pick up its exit status, and
1186        complain if it did anything other than exit with status 0.
1187
1188        We don't have to worry about killing the child, if the sync pipe
1189        returned an error. Usually this error is caused as the child killed itself
1190        while going down. Even in the rare cases that this isn't the case,
1191        the child will get an error when writing to the broken pipe the next time,
1192        cleaning itself up then. */
1193     sync_pipe_wait_for_child(capture_opts);
1194
1195 #ifdef _WIN32
1196     ws_close(capture_opts->signal_pipe_write_fd);
1197 #endif
1198     capture_input_closed(capture_opts);
1199     return FALSE;
1200   }
1201
1202   /* we got a valid message block from the child, process it */
1203   switch(indicator) {
1204   case SP_FILE:
1205     if(!capture_input_new_file(capture_opts, buffer)) {
1206       g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_input_cb: file failed, closing capture");
1207
1208       /* We weren't able to open the new capture file; user has been
1209          alerted. Close the sync pipe. */
1210       ws_close(source);
1211
1212       /* the child has send us a filename which we couldn't open.
1213          this probably means, the child is creating files faster than we can handle it.
1214          this should only be the case for very fast file switches
1215          we can't do much more than telling the child to stop
1216          (this is the "emergency brake" if user e.g. wants to switch files every second) */
1217       sync_pipe_stop(capture_opts);
1218     }
1219     break;
1220   case SP_PACKET_COUNT:
1221     nread = atoi(buffer);
1222     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_input_cb: new packets %u", nread);
1223     capture_input_new_packets(capture_opts, nread);
1224     break;
1225   case SP_ERROR_MSG:
1226     /* convert primary message */
1227     pipe_convert_header(buffer, 4, &indicator, &primary_len);
1228     primary_msg = buffer+4;
1229     /* convert secondary message */
1230     pipe_convert_header(primary_msg + primary_len, 4, &indicator, &secondary_len);
1231     secondary_msg = primary_msg + primary_len + 4;
1232     /* message output */
1233     capture_input_error_message(capture_opts, primary_msg, secondary_msg);
1234     /* the capture child will close the sync_pipe, nothing to do for now */
1235     /* (an error message doesn't mean we have to stop capturing) */
1236     break;
1237   case SP_BAD_FILTER:
1238     capture_input_cfilter_error_message(capture_opts, buffer);
1239     /* the capture child will close the sync_pipe, nothing to do for now */
1240     break;
1241   case SP_DROPS:
1242     capture_input_drops(capture_opts, (guint32)strtoul(buffer, NULL, 10));
1243     break;
1244   default:
1245     g_assert_not_reached();
1246   }
1247
1248   return TRUE;
1249 }
1250
1251
1252
1253 /* the child process is going down, wait until it's completely terminated */
1254 static void
1255 sync_pipe_wait_for_child(capture_options *capture_opts)
1256 {
1257   int  wstatus;
1258
1259
1260   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_wait_for_child: wait till child closed");
1261   g_assert(capture_opts->fork_child != -1);
1262
1263 #ifdef _WIN32
1264   if (_cwait(&wstatus, capture_opts->fork_child, _WAIT_CHILD) == -1) {
1265     report_failure("Child capture process stopped unexpectedly (errno:%u)",
1266                    errno);
1267   }
1268 #else
1269   if (wait(&wstatus) != -1) {
1270     if (WIFEXITED(wstatus)) {
1271       /* The child exited; display its exit status, if it seems uncommon (0=ok, 1=error) */
1272       /* the child will inform us about errors through the sync_pipe, which will popup */
1273       /* an error message, so don't popup another one */
1274
1275       /* If there are situations where the child won't send us such an error message, */
1276       /* this should be fixed in the child and not here! */
1277       if (WEXITSTATUS(wstatus) != 0 && WEXITSTATUS(wstatus) != 1) {
1278         report_failure("Child capture process exited: exit status %d",
1279                        WEXITSTATUS(wstatus));
1280       }
1281     } else if (WIFSTOPPED(wstatus)) {
1282       /* It stopped, rather than exiting.  "Should not happen." */
1283       report_failure("Child capture process stopped: %s",
1284                      sync_pipe_signame(WSTOPSIG(wstatus)));
1285     } else if (WIFSIGNALED(wstatus)) {
1286       /* It died with a signal. */
1287       report_failure("Child capture process died: %s%s",
1288                      sync_pipe_signame(WTERMSIG(wstatus)),
1289                      WCOREDUMP(wstatus) ? " - core dumped" : "");
1290     } else {
1291       /* What?  It had to either have exited, or stopped, or died with
1292          a signal; what happened here? */
1293       report_failure("Child capture process died: wait status %#o", wstatus);
1294     }
1295   }
1296 #endif
1297
1298   /* No more child process. */
1299   capture_opts->fork_child = -1;
1300
1301   g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_wait_for_child: capture child closed");
1302 }
1303
1304
1305 #ifndef _WIN32
1306 /* convert signal to corresponding name */
1307 static const char *
1308 sync_pipe_signame(int sig)
1309 {
1310   const char *sigmsg;
1311   static char sigmsg_buf[6+1+3+1];
1312
1313   switch (sig) {
1314
1315   case SIGHUP:
1316     sigmsg = "Hangup";
1317     break;
1318
1319   case SIGINT:
1320     sigmsg = "Interrupted";
1321     break;
1322
1323   case SIGQUIT:
1324     sigmsg = "Quit";
1325     break;
1326
1327   case SIGILL:
1328     sigmsg = "Illegal instruction";
1329     break;
1330
1331   case SIGTRAP:
1332     sigmsg = "Trace trap";
1333     break;
1334
1335   case SIGABRT:
1336     sigmsg = "Abort";
1337     break;
1338
1339   case SIGFPE:
1340     sigmsg = "Arithmetic exception";
1341     break;
1342
1343   case SIGKILL:
1344     sigmsg = "Killed";
1345     break;
1346
1347   case SIGBUS:
1348     sigmsg = "Bus error";
1349     break;
1350
1351   case SIGSEGV:
1352     sigmsg = "Segmentation violation";
1353     break;
1354
1355   /* http://metalab.unc.edu/pub/Linux/docs/HOWTO/GCC-HOWTO
1356      Linux is POSIX compliant.  These are not POSIX-defined signals ---
1357      ISO/IEC 9945-1:1990 (IEEE Std 1003.1-1990), paragraph B.3.3.1.1 sez:
1358
1359         ``The signals SIGBUS, SIGEMT, SIGIOT, SIGTRAP, and SIGSYS
1360         were omitted from POSIX.1 because their behavior is
1361         implementation dependent and could not be adequately catego-
1362         rized.  Conforming implementations may deliver these sig-
1363         nals, but must document the circumstances under which they
1364         are delivered and note any restrictions concerning their
1365         delivery.''
1366
1367      So we only check for SIGSYS on those systems that happen to
1368      implement them (a system can be POSIX-compliant and implement
1369      them, it's just that POSIX doesn't *require* a POSIX-compliant
1370      system to implement them).
1371    */
1372
1373 #ifdef SIGSYS
1374   case SIGSYS:
1375     sigmsg = "Bad system call";
1376     break;
1377 #endif
1378
1379   case SIGPIPE:
1380     sigmsg = "Broken pipe";
1381     break;
1382
1383   case SIGALRM:
1384     sigmsg = "Alarm clock";
1385     break;
1386
1387   case SIGTERM:
1388     sigmsg = "Terminated";
1389     break;
1390
1391   default:
1392         /* Returning a static buffer is ok in the context we use it here */
1393     g_snprintf(sigmsg_buf, sizeof sigmsg_buf, "Signal %d", sig);
1394     sigmsg = sigmsg_buf;
1395     break;
1396   }
1397   return sigmsg;
1398 }
1399 #endif
1400
1401
1402 #ifdef _WIN32
1403 /* tell the child through the signal pipe that we want to quit the capture */
1404 static void
1405 signal_pipe_capquit_to_child(capture_options *capture_opts)
1406 {
1407     const char quit_msg[] = "QUIT";
1408     int ret;
1409
1410
1411     g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "signal_pipe_capquit_to_child");
1412
1413     /* it doesn't matter *what* we send here, the first byte will stop the capture */
1414     /* simply sending a "QUIT" string */
1415     /*pipe_write_block(capture_opts->signal_pipe_write_fd, SP_QUIT, quit_msg);*/
1416     ret = write(capture_opts->signal_pipe_write_fd, quit_msg, sizeof quit_msg);
1417     if(ret == -1) {
1418         g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
1419               "signal_pipe_capquit_to_child: %d header: error %s", capture_opts->signal_pipe_write_fd, strerror(errno));
1420     }
1421 }
1422 #endif
1423
1424
1425 /* user wants to stop the capture run */
1426 void
1427 sync_pipe_stop(capture_options *capture_opts)
1428 {
1429 #ifdef _WIN32
1430   int count;
1431   DWORD childstatus;
1432   gboolean terminate = TRUE;
1433 #endif
1434
1435   if (capture_opts->fork_child != -1) {
1436 #ifndef _WIN32
1437     /* send the SIGINT signal to close the capture child gracefully. */
1438     int sts = kill(capture_opts->fork_child, SIGINT);
1439     if (sts != 0) {
1440         g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
1441               "Sending SIGINT to child failed: %s\n", strerror(errno));
1442     }
1443 #else
1444 #define STOP_SLEEP_TIME 500 /* ms */
1445 #define STOP_CHECK_TIME 50
1446     /* First, use the special signal pipe to try to close the capture child
1447      * gracefully.
1448      */
1449     signal_pipe_capquit_to_child(capture_opts);
1450
1451     /* Next, wait for the process to exit on its own */
1452     for (count = 0; count < STOP_SLEEP_TIME / STOP_CHECK_TIME; count++) {
1453       if (GetExitCodeProcess((HANDLE) capture_opts->fork_child, &childstatus) &&
1454               childstatus != STILL_ACTIVE) {
1455         terminate = FALSE;
1456         break;
1457       }
1458       Sleep(STOP_CHECK_TIME);
1459     }
1460
1461     /* Force the issue. */
1462     if (terminate) {
1463       g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
1464             "sync_pipe_stop: forcing child to exit");
1465       sync_pipe_kill(capture_opts->fork_child);
1466     }
1467 #endif
1468   }
1469 }
1470
1471
1472 /* Wireshark has to exit, force the capture child to close */
1473 void
1474 sync_pipe_kill(int fork_child)
1475 {
1476     if (fork_child != -1) {
1477 #ifndef _WIN32
1478         int sts = kill(fork_child, SIGTERM);    /* SIGTERM so it can clean up if necessary */
1479         if (sts != 0) {
1480             g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
1481                   "Sending SIGTERM to child failed: %s\n", strerror(errno));
1482         }
1483 #else
1484       /* Remark: This is not the preferred method of closing a process!
1485        * the clean way would be getting the process id of the child process,
1486        * then getting window handle hWnd of that process (using EnumChildWindows),
1487        * and then do a SendMessage(hWnd, WM_CLOSE, 0, 0)
1488        *
1489        * Unfortunately, I don't know how to get the process id from the
1490        * handle.  OpenProcess will get an handle (not a window handle)
1491        * from the process ID; it will not get a window handle from the
1492        * process ID.  (How could it?  A process can have more than one
1493        * window.  For that matter, a process might have *no* windows,
1494        * as a process running dumpcap, the normal child process program,
1495        * probably does.)
1496        *
1497        * Hint: GenerateConsoleCtrlEvent() will only work if both processes are
1498        * running in the same console; that's not necessarily the case for
1499        * us, as we might not be running in a console.
1500        * And this also will require to have the process id.
1501        */
1502         TerminateProcess((HANDLE) (fork_child), 0);
1503 #endif
1504     }
1505 }
1506
1507 #endif /* HAVE_LIBPCAP */