2 * Synchronisation between Wireshark capture parent and child instances
4 * Wireshark - Network traffic analyzer
5 * By Gerald Combs <gerald@wireshark.org>
6 * Copyright 1998 Gerald Combs
8 * This program is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU General Public License
10 * as published by the Free Software Foundation; either version 2
11 * of the License, or (at your option) any later version.
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
35 #include <wsutil/unicode-utils.h>
38 #ifdef HAVE_SYS_WAIT_H
39 # include <sys/wait.h>
42 #include "caputils/capture-pcap-util.h"
46 * Define various POSIX macros (and, in the case of WCOREDUMP, non-POSIX
47 * macros) on UNIX systems that don't have them.
50 # define WIFEXITED(status) (((status) & 0177) == 0)
53 # define WIFSTOPPED(status) (((status) & 0177) == 0177)
56 # define WIFSIGNALED(status) (!WIFSTOPPED(status) && !WIFEXITED(status))
59 # define WEXITSTATUS(status) ((status) >> 8)
62 # define WTERMSIG(status) ((status) & 0177)
65 # define WCOREDUMP(status) ((status) & 0200)
68 # define WSTOPSIG(status) ((status) >> 8)
72 #include <epan/packet.h>
73 #include <epan/prefs.h>
78 #include "ui/capture.h"
79 #include <capchild/capture_sync.h>
81 #include "sync_pipe.h"
84 #include "caputils/capture-wpcap.h"
87 #include "ui/ui_util.h"
89 #include <wsutil/filesystem.h>
90 #include <wsutil/file_util.h>
91 #include <wsutil/report_err.h>
98 #include <process.h> /* For spawning child process */
104 static void create_dummy_signal_pipe();
105 static HANDLE dummy_signal_pipe; /* Dummy named pipe which lets the child check for a dropped connection */
106 static gchar *dummy_control_id;
108 static const char *sync_pipe_signame(int);
112 static gboolean sync_pipe_input_cb(gint source, gpointer user_data);
113 static int sync_pipe_wait_for_child(ws_process_id fork_child, gchar **msgp);
114 static void pipe_convert_header(const guchar *header, int header_len, char *indicator, int *block_len);
115 static ssize_t pipe_read_block(int pipe_fd, char *indicator, int len, char *msg,
118 static void (*fetch_dumpcap_pid)(ws_process_id) = NULL;
122 capture_session_init(capture_session *cap_session, struct _capture_file *cf)
124 cap_session->cf = cf;
125 cap_session->fork_child = WS_INVALID_PID; /* invalid process handle */
127 cap_session->signal_pipe_write_fd = -1;
129 cap_session->state = CAPTURE_STOPPED;
131 cap_session->owner = getuid();
132 cap_session->group = getgid();
134 cap_session->count = 0;
135 cap_session->session_started = FALSE;
138 /* Append an arg (realloc) to an argc/argv array */
139 /* (add a string pointer to a NULL-terminated array of string pointers) */
141 sync_pipe_add_arg(char **args, int *argc, const char *arg)
143 /* Grow the array; "*argc" currently contains the number of string
144 pointers, *not* counting the NULL pointer at the end, so we have
145 to add 2 in order to get the new size of the array, including the
146 new pointer and the terminating NULL pointer. */
147 args = (char **)g_realloc( (gpointer) args, (*argc + 2) * sizeof (char *));
149 /* Stuff the pointer into the penultimate element of the array, which
150 is the one at the index specified by "*argc". */
151 args[*argc] = g_strdup(arg);
152 /* Now bump the count. */
155 /* We overwrite the NULL pointer; put it back right after the
165 /* Quote the argument element if necessary, so that it will get
166 * reconstructed correctly in the C runtime startup code. Note that
167 * the unquoting algorithm in the C runtime is really weird, and
168 * rather different than what Unix shells do. See stdargv.c in the C
169 * runtime sources (in the Platform SDK, in src/crt).
171 * Stolen from GLib's protect_argv(), an internal routine that quotes
172 * string in an argument list so that they arguments will be handled
173 * correctly in the command-line string passed to CreateProcess()
174 * if that string is constructed by gluing those strings together.
177 protect_arg (const gchar *argv)
180 const gchar *p = argv;
183 gboolean need_dblquotes = FALSE;
186 if (*p == ' ' || *p == '\t')
187 need_dblquotes = TRUE;
190 else if (*p == '\\') {
193 while (*pp && *pp == '\\')
202 q = new_arg = g_malloc (len + need_dblquotes*2 + 1);
211 else if (*p == '\\') {
214 while (*pp && *pp == '\\')
231 * Generate a string for a Win32 error.
233 #define ERRBUF_SIZE 1024
235 win32strerror(DWORD error)
237 static char errbuf[ERRBUF_SIZE+1];
241 FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
242 NULL, error, 0, errbuf, ERRBUF_SIZE, NULL);
245 * "FormatMessage()" "helpfully" sticks CR/LF at the end of the
246 * message. Get rid of it.
248 errlen = strlen(errbuf);
250 errbuf[errlen - 1] = '\0';
251 errbuf[errlen - 2] = '\0';
253 p = strchr(errbuf, '\0');
254 g_snprintf(p, (gulong)(sizeof errbuf - (p-errbuf)), " (%lu)", error);
259 * Generate a string for a Win32 exception code.
262 win32strexception(DWORD exception)
264 static char errbuf[ERRBUF_SIZE+1];
265 static const struct exception_msg {
269 { EXCEPTION_ACCESS_VIOLATION, "Access violation" },
270 { EXCEPTION_ARRAY_BOUNDS_EXCEEDED, "Array bounds exceeded" },
271 { EXCEPTION_BREAKPOINT, "Breakpoint" },
272 { EXCEPTION_DATATYPE_MISALIGNMENT, "Data type misalignment" },
273 { EXCEPTION_FLT_DENORMAL_OPERAND, "Denormal floating-point operand" },
274 { EXCEPTION_FLT_DIVIDE_BY_ZERO, "Floating-point divide by zero" },
275 { EXCEPTION_FLT_INEXACT_RESULT, "Floating-point inexact result" },
276 { EXCEPTION_FLT_INVALID_OPERATION, "Invalid floating-point operation" },
277 { EXCEPTION_FLT_OVERFLOW, "Floating-point overflow" },
278 { EXCEPTION_FLT_STACK_CHECK, "Floating-point stack check" },
279 { EXCEPTION_FLT_UNDERFLOW, "Floating-point underflow" },
280 { EXCEPTION_GUARD_PAGE, "Guard page violation" },
281 { EXCEPTION_ILLEGAL_INSTRUCTION, "Illegal instruction" },
282 { EXCEPTION_IN_PAGE_ERROR, "Page-in error" },
283 { EXCEPTION_INT_DIVIDE_BY_ZERO, "Integer divide by zero" },
284 { EXCEPTION_INT_OVERFLOW, "Integer overflow" },
285 { EXCEPTION_INVALID_DISPOSITION, "Invalid disposition" },
286 { EXCEPTION_INVALID_HANDLE, "Invalid handle" },
287 { EXCEPTION_NONCONTINUABLE_EXCEPTION, "Non-continuable exception" },
288 { EXCEPTION_PRIV_INSTRUCTION, "Privileged instruction" },
289 { EXCEPTION_SINGLE_STEP, "Single-step complete" },
290 { EXCEPTION_STACK_OVERFLOW, "Stack overflow" },
293 #define N_EXCEPTIONS (sizeof exceptions / sizeof exceptions[0])
296 for (i = 0; i < N_EXCEPTIONS; i++) {
297 if (exceptions[i].code == exception)
298 return exceptions[i].msg;
300 g_snprintf(errbuf, (gulong)sizeof errbuf, "Exception 0x%08x", exception);
305 /* Initialize an argument list and add dumpcap to it. */
307 init_pipe_args(int *argc) {
309 const char *progfile_dir;
312 progfile_dir = get_progfile_dir();
313 if (progfile_dir == NULL) {
317 /* Allocate the string pointer array with enough space for the
318 terminating NULL pointer. */
320 argv = (char **)g_malloc(sizeof (char *));
323 /* take Wireshark's absolute program path and replace "Wireshark" with "dumpcap" */
325 exename = g_strdup_printf("%s\\dumpcap.exe", progfile_dir);
327 exename = g_strdup_printf("%s/dumpcap", progfile_dir);
330 /* Make that the first argument in the argument list (argv[0]). */
331 argv = sync_pipe_add_arg(argv, argc, exename);
333 /* sync_pipe_add_arg strdupes exename, so we should free our copy */
339 #define ARGV_NUMBER_LEN 24
340 /* a new capture run: start a new dumpcap task and hand over parameters through command line */
342 sync_pipe_start(capture_options *capture_opts, capture_session *cap_session, void (*update_cb)(void))
344 char ssnap[ARGV_NUMBER_LEN];
345 char scount[ARGV_NUMBER_LEN];
346 char sfilesize[ARGV_NUMBER_LEN];
347 char sfile_duration[ARGV_NUMBER_LEN];
348 char sring_num_files[ARGV_NUMBER_LEN];
349 char sautostop_files[ARGV_NUMBER_LEN];
350 char sautostop_filesize[ARGV_NUMBER_LEN];
351 char sautostop_duration[ARGV_NUMBER_LEN];
352 #ifdef HAVE_PCAP_REMOTE
355 #ifdef HAVE_PCAP_SETSAMPLING
356 char ssampling[ARGV_NUMBER_LEN];
359 #ifdef CAN_SET_CAPTURE_BUFFER_SIZE
360 char buffer_size[ARGV_NUMBER_LEN];
364 HANDLE sync_pipe_read; /* pipe used to send messages from child to parent */
365 HANDLE sync_pipe_write; /* pipe used to send messages from child to parent */
366 HANDLE signal_pipe; /* named pipe used to send messages from parent to child (currently only stop) */
367 GString *args = g_string_sized_new(200);
369 SECURITY_ATTRIBUTES sa;
371 PROCESS_INFORMATION pi;
372 char control_id[ARGV_NUMBER_LEN];
373 gchar *signal_pipe_name;
376 int sync_pipe[2]; /* pipe used to send messages from child to parent */
377 enum PIPES { PIPE_READ, PIPE_WRITE }; /* Constants 0 and 1 for PIPE_READ and PIPE_WRITE */
379 int sync_pipe_read_fd;
384 interface_options interface_opts;
386 if (capture_opts->ifaces->len > 1)
387 capture_opts->use_pcapng = TRUE;
388 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_start");
389 capture_opts_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, capture_opts);
391 cap_session->fork_child = WS_INVALID_PID;
394 if (!extcaps_init_initerfaces(capture_opts)) {
395 report_failure("Unable to init extcaps. (tmp fifo already exists?)");
401 argv = init_pipe_args(&argc);
403 /* We don't know where to find dumpcap. */
404 report_failure("We don't know where to find dumpcap.");
408 if (capture_opts->ifaces->len > 1)
409 argv = sync_pipe_add_arg(argv, &argc, "-t");
411 if (capture_opts->use_pcapng)
412 argv = sync_pipe_add_arg(argv, &argc, "-n");
414 argv = sync_pipe_add_arg(argv, &argc, "-P");
416 if (capture_opts->capture_comment) {
417 argv = sync_pipe_add_arg(argv, &argc, "--capture-comment");
418 argv = sync_pipe_add_arg(argv, &argc, capture_opts->capture_comment);
421 if (capture_opts->multi_files_on) {
422 if (capture_opts->has_autostop_filesize) {
423 argv = sync_pipe_add_arg(argv, &argc, "-b");
424 g_snprintf(sfilesize, ARGV_NUMBER_LEN, "filesize:%u",capture_opts->autostop_filesize);
425 argv = sync_pipe_add_arg(argv, &argc, sfilesize);
428 if (capture_opts->has_file_duration) {
429 argv = sync_pipe_add_arg(argv, &argc, "-b");
430 g_snprintf(sfile_duration, ARGV_NUMBER_LEN, "duration:%d",capture_opts->file_duration);
431 argv = sync_pipe_add_arg(argv, &argc, sfile_duration);
434 if (capture_opts->has_ring_num_files) {
435 argv = sync_pipe_add_arg(argv, &argc, "-b");
436 g_snprintf(sring_num_files, ARGV_NUMBER_LEN, "files:%d",capture_opts->ring_num_files);
437 argv = sync_pipe_add_arg(argv, &argc, sring_num_files);
440 if (capture_opts->has_autostop_files) {
441 argv = sync_pipe_add_arg(argv, &argc, "-a");
442 g_snprintf(sautostop_files, ARGV_NUMBER_LEN, "files:%d",capture_opts->autostop_files);
443 argv = sync_pipe_add_arg(argv, &argc, sautostop_files);
446 if (capture_opts->has_autostop_filesize) {
447 argv = sync_pipe_add_arg(argv, &argc, "-a");
448 g_snprintf(sautostop_filesize, ARGV_NUMBER_LEN, "filesize:%u",capture_opts->autostop_filesize);
449 argv = sync_pipe_add_arg(argv, &argc, sautostop_filesize);
453 if (capture_opts->has_autostop_packets) {
454 argv = sync_pipe_add_arg(argv, &argc, "-c");
455 g_snprintf(scount, ARGV_NUMBER_LEN, "%d",capture_opts->autostop_packets);
456 argv = sync_pipe_add_arg(argv, &argc, scount);
459 if (capture_opts->has_autostop_duration) {
460 argv = sync_pipe_add_arg(argv, &argc, "-a");
461 g_snprintf(sautostop_duration, ARGV_NUMBER_LEN, "duration:%d",capture_opts->autostop_duration);
462 argv = sync_pipe_add_arg(argv, &argc, sautostop_duration);
465 if (capture_opts->group_read_access) {
466 argv = sync_pipe_add_arg(argv, &argc, "-g");
469 for (j = 0; j < capture_opts->ifaces->len; j++) {
470 interface_opts = g_array_index(capture_opts->ifaces, interface_options, j);
472 argv = sync_pipe_add_arg(argv, &argc, "-i");
474 if (interface_opts.extcap_fifo != NULL)
475 argv = sync_pipe_add_arg(argv, &argc, interface_opts.extcap_fifo);
478 argv = sync_pipe_add_arg(argv, &argc, interface_opts.name);
480 if (interface_opts.cfilter != NULL && strlen(interface_opts.cfilter) != 0) {
481 argv = sync_pipe_add_arg(argv, &argc, "-f");
482 argv = sync_pipe_add_arg(argv, &argc, interface_opts.cfilter);
484 if (interface_opts.snaplen != WTAP_MAX_PACKET_SIZE) {
485 argv = sync_pipe_add_arg(argv, &argc, "-s");
486 g_snprintf(ssnap, ARGV_NUMBER_LEN, "%d", interface_opts.snaplen);
487 argv = sync_pipe_add_arg(argv, &argc, ssnap);
490 if (interface_opts.linktype != -1) {
491 const char *linktype = linktype_val_to_name(interface_opts.linktype);
492 if ( linktype != NULL )
494 argv = sync_pipe_add_arg(argv, &argc, "-y");
495 argv = sync_pipe_add_arg(argv, &argc, linktype);
499 if (!interface_opts.promisc_mode) {
500 argv = sync_pipe_add_arg(argv, &argc, "-p");
503 #ifdef CAN_SET_CAPTURE_BUFFER_SIZE
504 if (interface_opts.buffer_size != DEFAULT_CAPTURE_BUFFER_SIZE) {
505 argv = sync_pipe_add_arg(argv, &argc, "-B");
506 if(interface_opts.buffer_size == 0x00)
507 interface_opts.buffer_size = DEFAULT_CAPTURE_BUFFER_SIZE;
508 g_snprintf(buffer_size, ARGV_NUMBER_LEN, "%d", interface_opts.buffer_size);
509 argv = sync_pipe_add_arg(argv, &argc, buffer_size);
513 #ifdef HAVE_PCAP_CREATE
514 if (interface_opts.monitor_mode) {
515 argv = sync_pipe_add_arg(argv, &argc, "-I");
519 #ifdef HAVE_PCAP_REMOTE
520 if (interface_opts.datatx_udp)
521 argv = sync_pipe_add_arg(argv, &argc, "-u");
523 if (!interface_opts.nocap_rpcap)
524 argv = sync_pipe_add_arg(argv, &argc, "-r");
526 if (interface_opts.auth_type == CAPTURE_AUTH_PWD) {
527 argv = sync_pipe_add_arg(argv, &argc, "-A");
528 g_snprintf(sauth, sizeof(sauth), "%s:%s",
529 interface_opts.auth_username,
530 interface_opts.auth_password);
531 argv = sync_pipe_add_arg(argv, &argc, sauth);
535 #ifdef HAVE_PCAP_SETSAMPLING
536 if (interface_opts.sampling_method != CAPTURE_SAMP_NONE) {
537 argv = sync_pipe_add_arg(argv, &argc, "-m");
538 g_snprintf(ssampling, ARGV_NUMBER_LEN, "%s:%d",
539 interface_opts.sampling_method == CAPTURE_SAMP_BY_COUNT ? "count" :
540 interface_opts.sampling_method == CAPTURE_SAMP_BY_TIMER ? "timer" :
542 interface_opts.sampling_param);
543 argv = sync_pipe_add_arg(argv, &argc, ssampling);
548 /* dumpcap should be running in capture child mode (hidden feature) */
550 argv = sync_pipe_add_arg(argv, &argc, "-Z");
552 g_snprintf(control_id, ARGV_NUMBER_LEN, "%d", GetCurrentProcessId());
553 argv = sync_pipe_add_arg(argv, &argc, control_id);
555 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
559 if (capture_opts->save_file) {
560 argv = sync_pipe_add_arg(argv, &argc, "-w");
561 argv = sync_pipe_add_arg(argv, &argc, capture_opts->save_file);
563 for (i = 0; i < argc; i++) {
564 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "argv[%d]: %s", i, argv[i]);
568 /* init SECURITY_ATTRIBUTES */
569 sa.nLength = sizeof(SECURITY_ATTRIBUTES);
570 sa.bInheritHandle = TRUE;
571 sa.lpSecurityDescriptor = NULL;
573 /* Create a pipe for the child process */
574 /* (increase this value if you have trouble while fast capture file switches) */
575 if (! CreatePipe(&sync_pipe_read, &sync_pipe_write, &sa, 5120)) {
576 /* Couldn't create the pipe between parent and child. */
577 report_failure("Couldn't create sync pipe: %s",
578 win32strerror(GetLastError()));
579 for (i = 0; i < argc; i++) {
580 g_free( (gpointer) argv[i]);
582 g_free( (gpointer) argv);
586 /* Create the signal pipe */
587 signal_pipe_name = g_strdup_printf(SIGNAL_PIPE_FORMAT, control_id);
588 signal_pipe = CreateNamedPipe(utf_8to16(signal_pipe_name),
589 PIPE_ACCESS_OUTBOUND, PIPE_TYPE_BYTE, 1, 65535, 65535, 0, NULL);
590 g_free(signal_pipe_name);
592 if (signal_pipe == INVALID_HANDLE_VALUE) {
593 /* Couldn't create the signal pipe between parent and child. */
594 report_failure("Couldn't create signal pipe: %s",
595 win32strerror(GetLastError()));
596 for (i = 0; i < argc; i++) {
597 g_free( (gpointer) argv[i]);
599 g_free( (gpointer) argv);
603 /* init STARTUPINFO */
604 memset(&si, 0, sizeof(si));
607 si.dwFlags = STARTF_USESHOWWINDOW;
608 si.wShowWindow = SW_SHOW;
610 si.dwFlags = STARTF_USESTDHANDLES|STARTF_USESHOWWINDOW;
611 si.wShowWindow = SW_HIDE; /* this hides the console window */
613 /* needs first a check if NULL *
614 * otherwise wouldn't work with non extcap interfaces */
615 if(interface_opts.extcap_fifo != NULL)
617 if(strncmp(interface_opts.extcap_fifo,"\\\\.\\pipe\\",9)== 0)
619 si.hStdInput = extcap_get_win32_handle();
624 si.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
626 si.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE);
627 si.hStdError = sync_pipe_write;
628 /*si.hStdError = (HANDLE) _get_osfhandle(2);*/
631 /* convert args array into a single string */
632 /* XXX - could change sync_pipe_add_arg() instead */
633 /* there is a drawback here: the length is internally limited to 1024 bytes */
634 for(i=0; argv[i] != 0; i++) {
635 if(i != 0) g_string_append_c(args, ' '); /* don't prepend a space before the path!!! */
636 quoted_arg = protect_arg(argv[i]);
637 g_string_append(args, quoted_arg);
642 if(!CreateProcess(utf_8to16(argv[0]), utf_8to16(args->str), NULL, NULL, TRUE,
643 CREATE_NEW_CONSOLE, NULL, NULL, &si, &pi)) {
644 report_failure("Couldn't run %s in child process: %s",
645 args->str, win32strerror(GetLastError()));
646 CloseHandle(sync_pipe_read);
647 CloseHandle(sync_pipe_write);
648 for (i = 0; i < argc; i++) {
649 g_free( (gpointer) argv[i]);
651 g_free( (gpointer) argv);
654 cap_session->fork_child = pi.hProcess;
655 g_string_free(args, TRUE);
657 /* associate the operating system filehandle to a C run-time file handle */
658 /* (good file handle infos at: http://www.flounder.com/handles.htm) */
659 sync_pipe_read_fd = _open_osfhandle( (intptr_t) sync_pipe_read, _O_BINARY);
661 /* associate the operating system filehandle to a C run-time file handle */
662 cap_session->signal_pipe_write_fd = _open_osfhandle( (intptr_t) signal_pipe, _O_BINARY);
665 if (pipe(sync_pipe) < 0) {
666 /* Couldn't create the pipe between parent and child. */
667 report_failure("Couldn't create sync pipe: %s", g_strerror(errno));
668 for (i = 0; i < argc; i++) {
669 g_free( (gpointer) argv[i]);
675 if ((cap_session->fork_child = fork()) == 0) {
677 * Child process - run dumpcap with the right arguments to make
678 * it just capture with the specified capture parameters
680 dup2(sync_pipe[PIPE_WRITE], 2);
681 ws_close(sync_pipe[PIPE_READ]);
682 execv(argv[0], argv);
683 g_snprintf(errmsg, sizeof errmsg, "Couldn't run %s in child process: %s",
684 argv[0], g_strerror(errno));
685 sync_pipe_errmsg_to_parent(2, errmsg, "");
687 /* Exit with "_exit()", so that we don't close the connection
688 to the X server (and cause stuff buffered up by our parent but
689 not yet sent to be sent, as that stuff should only be sent by
690 our parent). We've sent an error message to the parent, so
691 we exit with an exit status of 1 (any exit status other than
692 0 or 1 will cause an additional message to report that exit
693 status, over and above the error message we sent to the parent). */
697 if (fetch_dumpcap_pid && cap_session->fork_child > 0)
698 fetch_dumpcap_pid(cap_session->fork_child);
700 sync_pipe_read_fd = sync_pipe[PIPE_READ];
703 for (i = 0; i < argc; i++) {
704 g_free( (gpointer) argv[i]);
707 /* Parent process - read messages from the child process over the
709 g_free( (gpointer) argv); /* free up arg array */
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). */
716 CloseHandle(sync_pipe_write);
718 ws_close(sync_pipe[PIPE_WRITE]);
721 if (cap_session->fork_child == WS_INVALID_PID) {
722 /* We couldn't even create the child process. */
723 report_failure("Couldn't create child process: %s", g_strerror(errno));
724 ws_close(sync_pipe_read_fd);
726 ws_close(cap_session->signal_pipe_write_fd);
731 cap_session->fork_child_status = 0;
732 cap_session->capture_opts = capture_opts;
734 /* we might wait for a moment till child is ready, so update screen now */
735 if (update_cb) update_cb();
737 /* We were able to set up to read the capture file;
738 arrange that our callback be called whenever it's possible
739 to read from the sync pipe, so that it's called when
740 the child process wants to tell us something. */
742 /* we have a running capture, now wait for the real capture filename */
743 pipe_input_set_handler(sync_pipe_read_fd, (gpointer) cap_session,
744 &cap_session->fork_child, sync_pipe_input_cb);
750 * Open two pipes to dumpcap with the supplied arguments, one for its
751 * standard output and one for its standard error.
753 * On success, *msg is unchanged and 0 is returned; data_read_fd,
754 * messsage_read_fd, and fork_child point to the standard output pipe's
755 * file descriptor, the standard error pipe's file descriptor, and
756 * the child's PID/handle, respectively.
758 * On failure, *msg points to an error message for the failure, and -1 is
759 * returned, in which case *msg must be freed with g_free().
761 /* XXX - This duplicates a lot of code in sync_pipe_start() */
762 /* XXX - assumes PIPE_BUF_SIZE > SP_MAX_MSG_LEN */
763 #define PIPE_BUF_SIZE 5120
765 sync_pipe_open_command(char** argv, int *data_read_fd,
766 int *message_read_fd, ws_process_id *fork_child, gchar **msg, void(*update_cb)(void))
768 enum PIPES { PIPE_READ, PIPE_WRITE }; /* Constants 0 and 1 for PIPE_READ and PIPE_WRITE */
770 HANDLE sync_pipe[2]; /* pipe used to send messages from child to parent */
771 HANDLE data_pipe[2]; /* pipe used to send data from child to parent */
772 GString *args = g_string_sized_new(200);
774 SECURITY_ATTRIBUTES sa;
776 PROCESS_INFORMATION pi;
779 int sync_pipe[2]; /* pipe used to send messages from child to parent */
780 int data_pipe[2]; /* pipe used to send data from child to parent */
783 *fork_child = WS_INVALID_PID;
785 *message_read_fd = -1;
786 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_open_command");
789 /* We can't return anything */
791 g_string_free(args, TRUE);
797 /* init SECURITY_ATTRIBUTES */
798 sa.nLength = sizeof(SECURITY_ATTRIBUTES);
799 sa.bInheritHandle = TRUE;
800 sa.lpSecurityDescriptor = NULL;
802 /* Create a pipe for the child process to send us messages */
803 /* (increase this value if you have trouble while fast capture file switches) */
804 if (! CreatePipe(&sync_pipe[PIPE_READ], &sync_pipe[PIPE_WRITE], &sa, 5120)) {
805 /* Couldn't create the message pipe between parent and child. */
806 *msg = g_strdup_printf("Couldn't create sync pipe: %s",
807 win32strerror(GetLastError()));
808 for (i = 0; argv[i] != NULL; i++) {
809 g_free( (gpointer) argv[i]);
811 g_free( (gpointer) argv);
815 /* Create a pipe for the child process to send us data */
816 /* (increase this value if you have trouble while fast capture file switches) */
817 if (! CreatePipe(&data_pipe[PIPE_READ], &data_pipe[PIPE_WRITE], &sa, 5120)) {
818 /* Couldn't create the message pipe between parent and child. */
819 *msg = g_strdup_printf("Couldn't create data pipe: %s",
820 win32strerror(GetLastError()));
821 CloseHandle(sync_pipe[PIPE_READ]);
822 CloseHandle(sync_pipe[PIPE_WRITE]);
823 for (i = 0; argv[i] != NULL; i++) {
824 g_free( (gpointer) argv[i]);
826 g_free( (gpointer) argv);
830 /* init STARTUPINFO */
831 memset(&si, 0, sizeof(si));
834 si.dwFlags = STARTF_USESHOWWINDOW;
835 si.wShowWindow = SW_SHOW;
837 si.dwFlags = STARTF_USESTDHANDLES|STARTF_USESHOWWINDOW;
838 si.wShowWindow = SW_HIDE; /* this hides the console window */
839 si.hStdInput = NULL; /* handle for named pipe*/
841 si.hStdOutput = data_pipe[PIPE_WRITE];
842 si.hStdError = sync_pipe[PIPE_WRITE];
845 /* convert args array into a single string */
846 /* XXX - could change sync_pipe_add_arg() instead */
847 /* there is a drawback here: the length is internally limited to 1024 bytes */
848 for(i=0; argv[i] != 0; i++) {
849 if(i != 0) g_string_append_c(args, ' '); /* don't prepend a space before the path!!! */
850 quoted_arg = protect_arg(argv[i]);
851 g_string_append(args, quoted_arg);
856 if(!CreateProcess(utf_8to16(argv[0]), utf_8to16(args->str), NULL, NULL, TRUE,
857 CREATE_NEW_CONSOLE, NULL, NULL, &si, &pi)) {
858 *msg = g_strdup_printf("Couldn't run %s in child process: %s",
859 args->str, win32strerror(GetLastError()));
860 CloseHandle(data_pipe[PIPE_READ]);
861 CloseHandle(data_pipe[PIPE_WRITE]);
862 CloseHandle(sync_pipe[PIPE_READ]);
863 CloseHandle(sync_pipe[PIPE_WRITE]);
864 for (i = 0; argv[i] != NULL; i++) {
865 g_free( (gpointer) argv[i]);
867 g_free( (gpointer) argv);
870 *fork_child = pi.hProcess;
871 g_string_free(args, TRUE);
873 /* associate the operating system filehandles to C run-time file handles */
874 /* (good file handle infos at: http://www.flounder.com/handles.htm) */
875 *data_read_fd = _open_osfhandle( (intptr_t) data_pipe[PIPE_READ], _O_BINARY);
876 *message_read_fd = _open_osfhandle( (intptr_t) sync_pipe[PIPE_READ], _O_BINARY);
878 /* Create a pipe for the child process to send us messages */
879 if (pipe(sync_pipe) < 0) {
880 /* Couldn't create the message pipe between parent and child. */
881 *msg = g_strdup_printf("Couldn't create sync pipe: %s", g_strerror(errno));
882 for (i = 0; argv[i] != NULL; i++) {
883 g_free( (gpointer) argv[i]);
889 /* Create a pipe for the child process to send us data */
890 if (pipe(data_pipe) < 0) {
891 /* Couldn't create the data pipe between parent and child. */
892 *msg = g_strdup_printf("Couldn't create data pipe: %s", g_strerror(errno));
893 ws_close(sync_pipe[PIPE_READ]);
894 ws_close(sync_pipe[PIPE_WRITE]);
895 for (i = 0; argv[i] != NULL; i++) {
896 g_free( (gpointer) argv[i]);
902 if ((*fork_child = fork()) == 0) {
904 * Child process - run dumpcap with the right arguments to make
905 * it just capture with the specified capture parameters
907 dup2(data_pipe[PIPE_WRITE], 1);
908 ws_close(data_pipe[PIPE_READ]);
909 ws_close(data_pipe[PIPE_WRITE]);
910 dup2(sync_pipe[PIPE_WRITE], 2);
911 ws_close(sync_pipe[PIPE_READ]);
912 ws_close(sync_pipe[PIPE_WRITE]);
913 execv(argv[0], argv);
914 g_snprintf(errmsg, sizeof errmsg, "Couldn't run %s in child process: %s",
915 argv[0], g_strerror(errno));
916 sync_pipe_errmsg_to_parent(2, errmsg, "");
918 /* Exit with "_exit()", so that we don't close the connection
919 to the X server (and cause stuff buffered up by our parent but
920 not yet sent to be sent, as that stuff should only be sent by
921 our parent). We've sent an error message to the parent, so
922 we exit with an exit status of 1 (any exit status other than
923 0 or 1 will cause an additional message to report that exit
924 status, over and above the error message we sent to the parent). */
928 if (fetch_dumpcap_pid && *fork_child > 0)
929 fetch_dumpcap_pid(*fork_child);
931 *data_read_fd = data_pipe[PIPE_READ];
932 *message_read_fd = sync_pipe[PIPE_READ];
935 for (i = 0; argv[i] != NULL; i++) {
936 g_free( (gpointer) argv[i]);
939 /* Parent process - read messages from the child process over the
941 g_free( (gpointer) argv); /* free up arg array */
943 /* Close the write sides of the pipes, so that only the child has them
944 open, and thus they completely close, and thus return to us
945 an EOF indication, if the child closes them (either deliberately
946 or by exiting abnormally). */
948 CloseHandle(data_pipe[PIPE_WRITE]);
949 CloseHandle(sync_pipe[PIPE_WRITE]);
951 ws_close(data_pipe[PIPE_WRITE]);
952 ws_close(sync_pipe[PIPE_WRITE]);
955 if (*fork_child == WS_INVALID_PID) {
956 /* We couldn't even create the child process. */
957 *msg = g_strdup_printf("Couldn't create child process: %s", g_strerror(errno));
958 ws_close(*data_read_fd);
959 ws_close(*message_read_fd);
963 /* we might wait for a moment till child is ready, so update screen now */
964 if (update_cb) update_cb();
969 * Close the pipes we're using to read from dumpcap, and wait for it
970 * to exit. On success, *msgp is unchanged, and the exit status of
971 * dumpcap is returned. On failure (which includes "dumpcap exited
972 * due to being killed by a signal or an exception"), *msgp points
973 * to an error message for the failure, and -1 is returned. In the
974 * latter case, *msgp must be freed with g_free().
977 sync_pipe_close_command(int *data_read_fd, int *message_read_fd,
978 ws_process_id *fork_child, gchar **msgp)
980 ws_close(*data_read_fd);
981 if (message_read_fd != NULL)
982 ws_close(*message_read_fd);
985 /* XXX - Should we signal the child somehow? */
986 sync_pipe_kill(*fork_child);
989 return sync_pipe_wait_for_child(*fork_child, msgp);
993 * Run dumpcap with the supplied arguments.
995 * On success, *data points to a buffer containing the dumpcap output,
996 * *primary_msg and *secondary_message are NULL, and 0 is returned; *data
997 * must be freed with g_free().
999 * On failure, *data is NULL, *primary_msg points to an error message,
1000 * *secondary_msg either points to an additional error message or is
1001 * NULL, and -1 is returned; *primary_msg, and *secondary_msg if not NULL,
1002 * must be freed with g_free().
1004 /* XXX - This duplicates a lot of code in sync_pipe_start() */
1005 /* XXX - assumes PIPE_BUF_SIZE > SP_MAX_MSG_LEN */
1006 #define PIPE_BUF_SIZE 5120
1008 sync_pipe_run_command_actual(char** argv, gchar **data, gchar **primary_msg,
1009 gchar **secondary_msg, void(*update_cb)(void))
1012 int data_pipe_read_fd, sync_pipe_read_fd, ret;
1013 ws_process_id fork_child;
1015 gchar buffer[PIPE_BUF_SIZE+1] = {0};
1018 int primary_msg_len;
1019 char *primary_msg_text;
1020 int secondary_msg_len;
1021 char *secondary_msg_text;
1023 GString *data_buf = NULL;
1026 ret = sync_pipe_open_command(argv, &data_pipe_read_fd, &sync_pipe_read_fd,
1027 &fork_child, &msg, update_cb);
1030 *secondary_msg = NULL;
1036 * We were able to set up to read dumpcap's output. Do so.
1038 * First, wait for an SP_ERROR_MSG message or SP_SUCCESS message.
1040 nread = pipe_read_block(sync_pipe_read_fd, &indicator, SP_MAX_MSG_LEN,
1041 buffer, primary_msg);
1043 /* We got a read error from the sync pipe, or we got no data at
1044 all from the sync pipe, so we're not going to be getting any
1045 data or error message from the child process. Pick up its
1046 exit status, and complain.
1048 We don't have to worry about killing the child, if the sync pipe
1049 returned an error. Usually this error is caused as the child killed
1050 itself while going down. Even in the rare cases that this isn't the
1051 case, the child will get an error when writing to the broken pipe
1052 the next time, cleaning itself up then. */
1053 ret = sync_pipe_wait_for_child(fork_child, &wait_msg);
1055 /* We got an EOF from the sync pipe. That means that it exited
1056 before giving us any data to read. If ret is -1, we report
1057 that as a bad exit (e.g., exiting due to a signal); otherwise,
1058 we report it as a premature exit. */
1060 *primary_msg = wait_msg;
1062 *primary_msg = g_strdup("Child dumpcap closed sync pipe prematurely");
1064 /* We got an error from the sync pipe. If ret is -1, report
1065 both the sync pipe I/O error and the wait error. */
1067 combined_msg = g_strdup_printf("%s\n\n%s", *primary_msg, wait_msg);
1068 g_free(*primary_msg);
1070 *primary_msg = combined_msg;
1073 *secondary_msg = NULL;
1079 /* we got a valid message block from the child, process it */
1084 * Error from dumpcap; there will be a primary message and a
1085 * secondary message.
1088 /* convert primary message */
1089 pipe_convert_header((guchar*)buffer, 4, &indicator, &primary_msg_len);
1090 primary_msg_text = buffer+4;
1091 /* convert secondary message */
1092 pipe_convert_header((guchar*)primary_msg_text + primary_msg_len, 4, &indicator,
1093 &secondary_msg_len);
1094 secondary_msg_text = primary_msg_text + primary_msg_len + 4;
1095 /* the capture child will close the sync_pipe, nothing to do */
1098 * Pick up the child status.
1100 ret = sync_pipe_close_command(&data_pipe_read_fd, &sync_pipe_read_fd,
1104 * Child process failed unexpectedly, or wait failed; msg is the
1108 *secondary_msg = NULL;
1111 * Child process failed, but returned the expected exit status.
1112 * Return the messages it gave us, and indicate failure.
1114 *primary_msg = g_strdup(primary_msg_text);
1115 *secondary_msg = g_strdup(secondary_msg_text);
1122 /* read the output from the command */
1123 data_buf = g_string_new("");
1124 while ((count = ws_read(data_pipe_read_fd, buffer, PIPE_BUF_SIZE)) > 0) {
1125 buffer[count] = '\0';
1126 g_string_append(data_buf, buffer);
1130 * Pick up the child status.
1132 ret = sync_pipe_close_command(&data_pipe_read_fd, &sync_pipe_read_fd,
1136 * Child process failed unexpectedly, or wait failed; msg is the
1140 *secondary_msg = NULL;
1141 g_string_free(data_buf, TRUE);
1145 * Child process succeeded.
1147 *primary_msg = NULL;
1148 *secondary_msg = NULL;
1149 *data = g_string_free(data_buf, FALSE);
1155 * Pick up the child status.
1157 ret = sync_pipe_close_command(&data_pipe_read_fd, &sync_pipe_read_fd,
1161 * Child process failed unexpectedly, or wait failed; msg is the
1165 *secondary_msg = NULL;
1168 * Child process returned an unknown status.
1170 *primary_msg = g_strdup_printf("dumpcap process gave an unexpected message type: 0x%02x",
1172 *secondary_msg = NULL;
1181 /* centralised logging and timing for sync_pipe_run_command_actual(),
1182 * redirects to sync_pipe_run_command_actual()
1185 sync_pipe_run_command(char** argv, gchar **data, gchar **primary_msg,
1186 gchar **secondary_msg, void (*update_cb)(void))
1189 GTimeVal start_time;
1192 int logging_enabled;
1194 /* check if logging is actually enabled, otherwise don't expend the CPU generating logging */
1195 logging_enabled=( (G_LOG_LEVEL_DEBUG | G_LOG_LEVEL_INFO) & G_LOG_LEVEL_MASK & prefs.console_log_level);
1196 if(logging_enabled){
1197 g_get_current_time(&start_time);
1198 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_INFO, "sync_pipe_run_command() starts");
1199 for(i=0; argv[i] != 0; i++) {
1200 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, " argv[%d]: %s", i, argv[i]);
1203 /* do the actual sync pipe run command */
1204 ret=sync_pipe_run_command_actual(argv, data, primary_msg, secondary_msg, update_cb);
1206 if(logging_enabled){
1207 g_get_current_time(&end_time);
1208 elapsed = (float) ((end_time.tv_sec - start_time.tv_sec) +
1209 ((end_time.tv_usec - start_time.tv_usec) / 1e6));
1211 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_INFO, "sync_pipe_run_command() ends, taking %.3fs, result=%d", elapsed, ret);
1219 sync_interface_set_80211_chan(const gchar *iface, const char *freq, const gchar *type,
1220 gchar **data, gchar **primary_msg,
1221 gchar **secondary_msg, void (*update_cb)(void))
1227 argv = init_pipe_args(&argc);
1230 *primary_msg = g_strdup("We don't know where to find dumpcap.");
1231 *secondary_msg = NULL;
1236 argv = sync_pipe_add_arg(argv, &argc, "-i");
1237 argv = sync_pipe_add_arg(argv, &argc, iface);
1240 opt = g_strdup_printf("%s,%s", freq, type);
1242 opt = g_strdup_printf("%s", freq);
1245 *primary_msg = g_strdup("Out of mem.");
1246 *secondary_msg = NULL;
1251 argv = sync_pipe_add_arg(argv, &argc, "-k");
1252 argv = sync_pipe_add_arg(argv, &argc, opt);
1255 /* Run dumpcap in capture child mode */
1256 argv = sync_pipe_add_arg(argv, &argc, "-Z");
1257 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
1260 ret = sync_pipe_run_command(argv, data, primary_msg, secondary_msg, update_cb);
1266 * Get the list of interfaces using dumpcap.
1268 * On success, *data points to a buffer containing the dumpcap output,
1269 * *primary_msg and *secondary_msg are NULL, and 0 is returned. *data
1270 * must be freed with g_free().
1272 * On failure, *data is NULL, *primary_msg points to an error message,
1273 * *secondary_msg either points to an additional error message or is
1274 * NULL, and -1 is returned; *primary_msg, and *secondary_msg if not NULL,
1275 * must be freed with g_free().
1278 sync_interface_list_open(gchar **data, gchar **primary_msg,
1279 gchar **secondary_msg, void (*update_cb)(void))
1284 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_interface_list_open");
1286 argv = init_pipe_args(&argc);
1289 *primary_msg = g_strdup("We don't know where to find dumpcap..");
1290 *secondary_msg = NULL;
1295 /* Ask for the interface list */
1296 argv = sync_pipe_add_arg(argv, &argc, "-D");
1299 /* Run dumpcap in capture child mode */
1300 argv = sync_pipe_add_arg(argv, &argc, "-Z");
1301 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
1303 return sync_pipe_run_command(argv, data, primary_msg, secondary_msg, update_cb);
1307 * Get the capabilities of an interface using dumpcap.
1309 * On success, *data points to a buffer containing the dumpcap output,
1310 * *primary_msg and *secondary_msg are NULL, and 0 is returned. *data
1311 * must be freed with g_free().
1313 * On failure, *data is NULL, *primary_msg points to an error message,
1314 * *secondary_msg either points to an additional error message or is
1315 * NULL, and -1 is returned; *primary_msg, and *secondary_msg if not NULL,
1316 * must be freed with g_free().
1319 sync_if_capabilities_open(const gchar *ifname, gboolean monitor_mode, const gchar* auth,
1320 gchar **data, gchar **primary_msg,
1321 gchar **secondary_msg, void (*update_cb)(void))
1326 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_if_capabilities_open");
1328 argv = init_pipe_args(&argc);
1331 *primary_msg = g_strdup("We don't know where to find dumpcap.");
1332 *secondary_msg = NULL;
1337 /* Ask for the interface capabilities */
1338 argv = sync_pipe_add_arg(argv, &argc, "-i");
1339 argv = sync_pipe_add_arg(argv, &argc, ifname);
1340 argv = sync_pipe_add_arg(argv, &argc, "-L");
1342 argv = sync_pipe_add_arg(argv, &argc, "-I");
1344 argv = sync_pipe_add_arg(argv, &argc, "-A");
1345 argv = sync_pipe_add_arg(argv, &argc, auth);
1349 /* Run dumpcap in capture child mode */
1350 argv = sync_pipe_add_arg(argv, &argc, "-Z");
1351 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
1353 return sync_pipe_run_command(argv, data, primary_msg, secondary_msg, update_cb);
1357 * Start getting interface statistics using dumpcap. On success, read_fd
1358 * contains the file descriptor for the pipe's stdout, *msg is unchanged,
1359 * and zero is returned. On failure, *msg will point to an error message
1360 * that must be g_free()d, and -1 will be returned.
1363 sync_interface_stats_open(int *data_read_fd, ws_process_id *fork_child, gchar **msg, void (*update_cb)(void))
1367 int message_read_fd, ret;
1369 gchar buffer[PIPE_BUF_SIZE+1] = {0};
1372 int primary_msg_len;
1373 char *primary_msg_text;
1374 int secondary_msg_len;
1375 /*char *secondary_msg_text;*/
1378 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_interface_stats_open");
1380 argv = init_pipe_args(&argc);
1383 *msg = g_strdup("We don't know where to find dumpcap.");
1387 /* Ask for the interface statistics */
1388 argv = sync_pipe_add_arg(argv, &argc, "-S");
1391 argv = sync_pipe_add_arg(argv, &argc, "-Z");
1393 create_dummy_signal_pipe();
1394 argv = sync_pipe_add_arg(argv, &argc, dummy_control_id);
1396 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
1399 ret = sync_pipe_open_command(argv, data_read_fd, &message_read_fd,
1400 fork_child, msg, update_cb);
1405 * We were able to set up to read dumpcap's output. Do so.
1407 * First, wait for an SP_ERROR_MSG message or SP_SUCCESS message.
1409 nread = pipe_read_block(message_read_fd, &indicator, SP_MAX_MSG_LEN,
1412 /* We got a read error from the sync pipe, or we got no data at
1413 all from the sync pipe, so we're not going to be getting any
1414 data or error message from the child process. Pick up its
1415 exit status, and complain.
1417 We don't have to worry about killing the child, if the sync pipe
1418 returned an error. Usually this error is caused as the child killed
1419 itself while going down. Even in the rare cases that this isn't the
1420 case, the child will get an error when writing to the broken pipe
1421 the next time, cleaning itself up then. */
1422 ret = sync_pipe_wait_for_child(*fork_child, &wait_msg);
1424 /* We got an EOF from the sync pipe. That means that it exited
1425 before giving us any data to read. If ret is -1, we report
1426 that as a bad exit (e.g., exiting due to a signal); otherwise,
1427 we report it as a premature exit. */
1431 *msg = g_strdup("Child dumpcap closed sync pipe prematurely");
1433 /* We got an error from the sync pipe. If ret is -1, report
1434 both the sync pipe I/O error and the wait error. */
1436 combined_msg = g_strdup_printf("%s\n\n%s", *msg, wait_msg);
1439 *msg = combined_msg;
1446 /* we got a valid message block from the child, process it */
1451 * Error from dumpcap; there will be a primary message and a
1452 * secondary message.
1455 /* convert primary message */
1456 pipe_convert_header((guchar*)buffer, 4, &indicator, &primary_msg_len);
1457 primary_msg_text = buffer+4;
1458 /* convert secondary message */
1459 pipe_convert_header((guchar*)primary_msg_text + primary_msg_len, 4, &indicator,
1460 &secondary_msg_len);
1461 /*secondary_msg_text = primary_msg_text + primary_msg_len + 4;*/
1462 /* the capture child will close the sync_pipe, nothing to do */
1465 * Pick up the child status.
1467 ret = sync_pipe_close_command(data_read_fd, &message_read_fd,
1471 * Child process failed unexpectedly, or wait failed; msg is the
1476 * Child process failed, but returned the expected exit status.
1477 * Return the messages it gave us, and indicate failure.
1479 *msg = g_strdup(primary_msg_text);
1485 /* Close the message pipe. */
1486 ws_close(message_read_fd);
1491 * Pick up the child status.
1493 ret = sync_pipe_close_command(data_read_fd, &message_read_fd,
1497 * Child process failed unexpectedly, or wait failed; msg is the
1502 * Child process returned an unknown status.
1504 *msg = g_strdup_printf("dumpcap process gave an unexpected message type: 0x%02x",
1513 /* Close down the stats process */
1515 sync_interface_stats_close(int *read_fd, ws_process_id *fork_child, gchar **msg)
1519 * Don't bother waiting for the child. sync_pipe_close_command
1520 * does this for us on Windows.
1522 sync_pipe_kill(*fork_child);
1524 return sync_pipe_close_command(read_fd, NULL, fork_child, msg);
1527 /* read a number of bytes from a pipe */
1528 /* (blocks until enough bytes read or an error occurs) */
1530 pipe_read_bytes(int pipe_fd, char *bytes, int required, char **msg)
1537 newly = read(pipe_fd, &bytes[offset], required);
1540 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1541 "read from pipe %d: EOF (capture closed?)", pipe_fd);
1548 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1549 "read from pipe %d: error(%u): %s", pipe_fd, error,
1551 *msg = g_strdup_printf("Error reading from sync pipe: %s",
1556 required -= (int)newly;
1564 static gboolean pipe_data_available(int pipe_fd) {
1565 #ifdef _WIN32 /* PeekNamedPipe */
1566 HANDLE hPipe = (HANDLE) _get_osfhandle(pipe_fd);
1569 if (hPipe == INVALID_HANDLE_VALUE)
1572 if (! PeekNamedPipe(hPipe, NULL, 0, NULL, &bytes_avail, NULL))
1575 if (bytes_avail > 0)
1580 struct timeval timeout;
1583 FD_SET(pipe_fd, &rfds);
1585 timeout.tv_usec = 0;
1587 if (select(pipe_fd+1, &rfds, NULL, NULL, &timeout) > 0)
1594 /* Read a line from a pipe, similar to fgets */
1596 sync_pipe_gets_nonblock(int pipe_fd, char *bytes, int max) {
1600 while(offset < max - 1) {
1602 if (! pipe_data_available(pipe_fd))
1604 newly = read(pipe_fd, &bytes[offset], 1);
1606 /* EOF - not necessarily an error */
1608 } else if (newly == -1) {
1610 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1611 "read from pipe %d: error(%u): %s", pipe_fd, errno, g_strerror(errno));
1613 } else if (bytes[offset] == '\n') {
1619 bytes[offset] = '\0';
1625 /* convert header values (indicator and 3-byte length) */
1627 pipe_convert_header(const guchar *header, int header_len, char *indicator, int *block_len) {
1629 g_assert(header_len == 4);
1631 /* convert header values */
1632 *indicator = header[0];
1633 *block_len = (header[1]&0xFF)<<16 | (header[2]&0xFF)<<8 | (header[3]&0xFF);
1636 /* read a message from the sending pipe in the standard format
1637 (1-byte message indicator, 3-byte message length (excluding length
1638 and indicator field), and the rest is the message) */
1640 pipe_read_block(int pipe_fd, char *indicator, int len, char *msg,
1647 /* read header (indicator and 3-byte length) */
1648 newly = pipe_read_bytes(pipe_fd, header, 4, err_msg);
1652 * Immediate EOF; if the capture child exits normally, this
1653 * is an "I'm done" indication, so don't report it as an
1656 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1657 "read %d got an EOF", pipe_fd);
1660 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1661 "read %d failed to read header: %lu", pipe_fd, (long)newly);
1664 * Short read, but not an immediate EOF.
1666 *err_msg = g_strdup_printf("Premature EOF reading from sync pipe: got only %ld bytes",
1672 /* convert header values */
1673 pipe_convert_header((guchar*)header, 4, indicator, &required);
1675 /* only indicator with no value? */
1677 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1678 "read %d indicator: %c empty value", pipe_fd, *indicator);
1682 /* does the data fit into the given buffer? */
1683 if(required > len) {
1684 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1685 "read %d length error, required %d > len %d, header: 0x%02x 0x%02x 0x%02x 0x%02x",
1686 pipe_fd, required, len,
1687 header[0], header[1], header[2], header[3]);
1689 /* we have a problem here, try to read some more bytes from the pipe to debug where the problem really is */
1690 memcpy(msg, header, sizeof(header));
1691 newly = read(pipe_fd, &msg[sizeof(header)], len-sizeof(header));
1692 if (newly < 0) { /* error */
1693 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1694 "read from pipe %d: error(%u): %s", pipe_fd, errno, g_strerror(errno));
1696 *err_msg = g_strdup_printf("Unknown message from dumpcap, try to show it as a string: %s",
1702 /* read the actual block data */
1703 newly = pipe_read_bytes(pipe_fd, msg, required, err_msg);
1704 if(newly != required) {
1706 *err_msg = g_strdup_printf("Unknown message from dumpcap, try to show it as a string: %s",
1712 /* XXX If message is "2part", the msg probably won't be sent to debug log correctly */
1713 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1714 "read %d ok indicator: %c len: %u msg: %s", pipe_fd, *indicator,
1721 /* There's stuff to read from the sync pipe, meaning the child has sent
1722 us a message, or the sync pipe has closed, meaning the child has
1723 closed it (perhaps because it exited). */
1725 sync_pipe_input_cb(gint source, gpointer user_data)
1727 capture_session *cap_session = (capture_session *)user_data;
1729 char buffer[SP_MAX_MSG_LEN+1] = {0};
1735 char *secondary_msg;
1736 char *wait_msg, *combined_msg;
1739 nread = pipe_read_block(source, &indicator, SP_MAX_MSG_LEN, buffer,
1742 /* We got a read error, or a bad message, or an EOF, from the sync pipe.
1744 If we got a read error or a bad message, nread is -1 and
1745 primary_msg is set to point to an error message. We don't
1746 have to worry about killing the child; usually this error
1747 is caused as the child killed itself while going down.
1748 Even in the rare cases that this isn't the case, the child
1749 will get an error when writing to the broken pipe the next time,
1750 cleaning itself up then.
1752 If we got an EOF, nread is 0 and primary_msg isn't set. This
1753 is an indication that the capture is finished. */
1754 ret = sync_pipe_wait_for_child(cap_session->fork_child, &wait_msg);
1756 /* We got an EOF from the sync pipe. That means that the capture
1757 child exited, and not in the middle of a message; we treat
1758 that as an indication that it's done, and only report an
1759 error if ret is -1, in which case wait_msg is the error
1762 primary_msg = wait_msg;
1764 /* We got an error from the sync pipe. If ret is -1, report
1765 both the sync pipe I/O error and the wait error. */
1767 combined_msg = g_strdup_printf("%s\n\n%s", primary_msg, wait_msg);
1768 g_free(primary_msg);
1770 primary_msg = combined_msg;
1774 /* No more child process. */
1775 cap_session->fork_child = WS_INVALID_PID;
1776 cap_session->fork_child_status = ret;
1779 ws_close(cap_session->signal_pipe_write_fd);
1782 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_input_cb: cleaning extcap pipe");
1783 extcap_cleanup(cap_session->capture_opts);
1785 capture_input_closed(cap_session, primary_msg);
1786 g_free(primary_msg);
1790 /* we got a valid message block from the child, process it */
1793 if(!capture_input_new_file(cap_session, buffer)) {
1794 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_input_cb: file failed, closing capture");
1796 /* We weren't able to open the new capture file; user has been
1797 alerted. Close the sync pipe. */
1800 /* The child has sent us a filename which we couldn't open.
1802 This could mean that the child is creating and deleting files
1803 (ring buffer mode) faster than we can handle it.
1805 That should only be the case for very fast file switches;
1806 We can't do much more than telling the child to stop.
1807 (This is the "emergency brake" if the user e.g. wants to
1808 switch files every second).
1810 This can also happen if the user specified "-", meaning
1811 "standard output", as the capture file. */
1812 sync_pipe_stop(cap_session);
1813 capture_input_closed(cap_session, NULL);
1817 case SP_PACKET_COUNT:
1818 npackets = atoi(buffer);
1819 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_input_cb: new packets %u", npackets);
1820 cap_session->count += npackets;
1821 capture_input_new_packets(cap_session, npackets);
1824 /* convert primary message */
1825 pipe_convert_header((guchar*)buffer, 4, &indicator, &primary_len);
1826 primary_msg = buffer+4;
1827 /* convert secondary message */
1828 pipe_convert_header((guchar*)primary_msg + primary_len, 4, &indicator, &secondary_len);
1829 secondary_msg = primary_msg + primary_len + 4;
1830 /* message output */
1831 capture_input_error_message(cap_session, primary_msg, secondary_msg);
1832 /* the capture child will close the sync_pipe, nothing to do for now */
1833 /* (an error message doesn't mean we have to stop capturing) */
1835 case SP_BAD_FILTER: {
1839 ch = strtok(buffer, ":");
1841 indx = (int)strtol(ch, NULL, 10);
1842 ch = strtok(NULL, ":");
1844 capture_input_cfilter_error_message(cap_session, indx, ch);
1845 /* the capture child will close the sync_pipe, nothing to do for now */
1849 capture_input_drops(cap_session, (guint32)strtoul(buffer, NULL, 10));
1852 g_assert_not_reached();
1861 * dumpcap is exiting; wait for it to exit. On success, *msgp is
1862 * unchanged, and the exit status of dumpcap is returned. On
1863 * failure (which includes "dumpcap exited due to being killed by
1864 * a signal or an exception"), *msgp points to an error message
1865 * for the failure, and -1 is returned. In the latter case, *msgp
1866 * must be freed with g_free().
1869 sync_pipe_wait_for_child(ws_process_id fork_child, gchar **msgp)
1871 int fork_child_status;
1873 int retry_waitpid = 3;
1876 GTimeVal start_time;
1881 * GLIB_CHECK_VERSION(2,28,0) adds g_get_real_time which could minimize or
1884 g_get_current_time(&start_time);
1886 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_wait_for_child: wait till child closed");
1887 g_assert(fork_child != WS_INVALID_PID);
1889 *msgp = NULL; /* assume no error */
1891 if (_cwait(&fork_child_status, (intptr_t) fork_child, _WAIT_CHILD) == -1) {
1892 *msgp = g_strdup_printf("Error from cwait(): %s", g_strerror(errno));
1896 * The child exited; return its exit status. Do not treat this as
1899 ret = fork_child_status;
1900 if ((fork_child_status & 0xC0000000) == ERROR_SEVERITY_ERROR) {
1901 /* Probably an exception code */
1902 *msgp = g_strdup_printf("Child dumpcap process died: %s",
1903 win32strexception(fork_child_status));
1908 while (--retry_waitpid >= 0) {
1909 if (waitpid(fork_child, &fork_child_status, 0) != -1) {
1910 if (WIFEXITED(fork_child_status)) {
1912 * The child exited; return its exit status. Do not treat this as
1915 ret = WEXITSTATUS(fork_child_status);
1916 } else if (WIFSTOPPED(fork_child_status)) {
1917 /* It stopped, rather than exiting. "Should not happen." */
1918 *msgp = g_strdup_printf("Child dumpcap process stopped: %s",
1919 sync_pipe_signame(WSTOPSIG(fork_child_status)));
1921 } else if (WIFSIGNALED(fork_child_status)) {
1922 /* It died with a signal. */
1923 *msgp = g_strdup_printf("Child dumpcap process died: %s%s",
1924 sync_pipe_signame(WTERMSIG(fork_child_status)),
1925 WCOREDUMP(fork_child_status) ? " - core dumped" : "");
1928 /* What? It had to either have exited, or stopped, or died with
1929 a signal; what happened here? */
1930 *msgp = g_strdup_printf("Bad status from waitpid(): %#o",
1934 } else if (errno != ECHILD) {
1935 *msgp = g_strdup_printf("Error from waitpid(): %s", g_strerror(errno));
1937 } else if (errno == EINTR) {
1938 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_WARNING, "sync_pipe_wait_for_child: waitpid returned EINTR. retrying.");
1941 /* errno == ECHILD ; echld might have already reaped the child */
1942 ret = fetch_dumpcap_pid ? 0 : -1;
1948 g_get_current_time(&end_time);
1949 elapsed = (float) ((end_time.tv_sec - start_time.tv_sec) +
1950 ((end_time.tv_usec - start_time.tv_usec) / 1e6));
1951 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_wait_for_child: capture child closed after %.3fs", elapsed);
1957 /* convert signal to corresponding name */
1959 sync_pipe_signame(int sig)
1962 static char sigmsg_buf[6+1+3+1];
1971 sigmsg = "Interrupted";
1979 sigmsg = "Illegal instruction";
1983 sigmsg = "Trace trap";
1991 sigmsg = "Arithmetic exception";
1999 sigmsg = "Bus error";
2003 sigmsg = "Segmentation violation";
2006 /* http://metalab.unc.edu/pub/Linux/docs/HOWTO/GCC-HOWTO
2007 Linux is POSIX compliant. These are not POSIX-defined signals ---
2008 ISO/IEC 9945-1:1990 (IEEE Std 1003.1-1990), paragraph B.3.3.1.1 sez:
2010 ``The signals SIGBUS, SIGEMT, SIGIOT, SIGTRAP, and SIGSYS
2011 were omitted from POSIX.1 because their behavior is
2012 implementation dependent and could not be adequately catego-
2013 rized. Conforming implementations may deliver these sig-
2014 nals, but must document the circumstances under which they
2015 are delivered and note any restrictions concerning their
2018 So we only check for SIGSYS on those systems that happen to
2019 implement them (a system can be POSIX-compliant and implement
2020 them, it's just that POSIX doesn't *require* a POSIX-compliant
2021 system to implement them).
2026 sigmsg = "Bad system call";
2031 sigmsg = "Broken pipe";
2035 sigmsg = "Alarm clock";
2039 sigmsg = "Terminated";
2043 /* Returning a static buffer is ok in the context we use it here */
2044 g_snprintf(sigmsg_buf, sizeof sigmsg_buf, "Signal %d", sig);
2045 sigmsg = sigmsg_buf;
2055 static void create_dummy_signal_pipe() {
2056 gchar *dummy_signal_pipe_name;
2058 if (dummy_signal_pipe != NULL) return;
2060 if (!dummy_control_id) {
2061 dummy_control_id = g_strdup_printf("%d.dummy", GetCurrentProcessId());
2064 /* Create the signal pipe */
2065 dummy_signal_pipe_name = g_strdup_printf(SIGNAL_PIPE_FORMAT, dummy_control_id);
2066 dummy_signal_pipe = CreateNamedPipe(utf_8to16(dummy_signal_pipe_name),
2067 PIPE_ACCESS_OUTBOUND, PIPE_TYPE_BYTE, 1, 65535, 65535, 0, NULL);
2068 g_free(dummy_signal_pipe_name);
2071 /* tell the child through the signal pipe that we want to quit the capture */
2073 signal_pipe_capquit_to_child(capture_session *cap_session)
2075 const char quit_msg[] = "QUIT";
2078 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "signal_pipe_capquit_to_child");
2080 /* it doesn't matter *what* we send here, the first byte will stop the capture */
2081 /* simply sending a "QUIT" string */
2082 /*pipe_write_block(cap_session->signal_pipe_write_fd, SP_QUIT, quit_msg);*/
2083 ret = write(cap_session->signal_pipe_write_fd, quit_msg, sizeof quit_msg);
2085 g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
2086 "signal_pipe_capquit_to_child: %d header: error %s", cap_session->signal_pipe_write_fd, g_strerror(errno));
2092 /* user wants to stop the capture run */
2094 sync_pipe_stop(capture_session *cap_session)
2099 gboolean terminate = TRUE;
2101 if (cap_session->fork_child != WS_INVALID_PID) {
2103 /* send the SIGINT signal to close the capture child gracefully. */
2104 int sts = kill(cap_session->fork_child, SIGINT);
2106 g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
2107 "Sending SIGINT to child failed: %s\n", g_strerror(errno));
2110 #define STOP_SLEEP_TIME 500 /* ms */
2111 #define STOP_CHECK_TIME 50
2112 /* First, use the special signal pipe to try to close the capture child
2115 signal_pipe_capquit_to_child(cap_session);
2117 /* Next, wait for the process to exit on its own */
2118 for (count = 0; count < STOP_SLEEP_TIME / STOP_CHECK_TIME; count++) {
2119 if (GetExitCodeProcess((HANDLE) cap_session->fork_child, &childstatus) &&
2120 childstatus != STILL_ACTIVE) {
2124 Sleep(STOP_CHECK_TIME);
2127 /* Force the issue. */
2129 g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
2130 "sync_pipe_stop: forcing child to exit");
2131 sync_pipe_kill(cap_session->fork_child);
2138 /* Wireshark has to exit, force the capture child to close */
2140 sync_pipe_kill(ws_process_id fork_child)
2142 if (fork_child != WS_INVALID_PID) {
2144 int sts = kill(fork_child, SIGTERM); /* SIGTERM so it can clean up if necessary */
2146 g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
2147 "Sending SIGTERM to child failed: %s\n", g_strerror(errno));
2150 /* Remark: This is not the preferred method of closing a process!
2151 * the clean way would be getting the process id of the child process,
2152 * then getting window handle hWnd of that process (using EnumChildWindows),
2153 * and then do a SendMessage(hWnd, WM_CLOSE, 0, 0)
2155 * Unfortunately, I don't know how to get the process id from the
2156 * handle. OpenProcess will get an handle (not a window handle)
2157 * from the process ID; it will not get a window handle from the
2158 * process ID. (How could it? A process can have more than one
2159 * window. For that matter, a process might have *no* windows,
2160 * as a process running dumpcap, the normal child process program,
2163 * Hint: GenerateConsoleCtrlEvent() will only work if both processes are
2164 * running in the same console; that's not necessarily the case for
2165 * us, as we might not be running in a console.
2166 * And this also will require to have the process id.
2168 TerminateProcess((HANDLE) (fork_child), 0);
2174 void capture_sync_set_fetch_dumpcap_pid_cb(void(*cb)(ws_process_id pid)) {
2175 fetch_dumpcap_pid = cb;
2178 #endif /* HAVE_LIBPCAP */