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.
44 #include <wsutil/unicode-utils.h>
47 #ifdef HAVE_SYS_WAIT_H
48 # include <sys/wait.h>
51 #include "capture-pcap-util.h"
55 * Define various POSIX macros (and, in the case of WCOREDUMP, non-POSIX
56 * macros) on UNIX systems that don't have them.
59 # define WIFEXITED(status) (((status) & 0177) == 0)
62 # define WIFSTOPPED(status) (((status) & 0177) == 0177)
65 # define WIFSIGNALED(status) (!WIFSTOPPED(status) && !WIFEXITED(status))
68 # define WEXITSTATUS(status) ((status) >> 8)
71 # define WTERMSIG(status) ((status) & 0177)
74 # define WCOREDUMP(status) ((status) & 0200)
77 # define WSTOPSIG(status) ((status) >> 8)
81 #include <epan/packet.h>
82 #include <epan/prefs.h>
88 #include "capture_sync.h"
90 #include "sync_pipe.h"
93 #include "capture-wpcap.h"
96 #include "ui/ui_util.h"
98 #include <wsutil/filesystem.h>
99 #include <wsutil/file_util.h>
100 #include <wsutil/report_err.h>
104 #include <process.h> /* For spawning child process */
110 static void create_dummy_signal_pipe();
111 static HANDLE dummy_signal_pipe; /* Dummy named pipe which lets the child check for a dropped connection */
112 static gchar *dummy_control_id;
114 static const char *sync_pipe_signame(int);
118 static gboolean sync_pipe_input_cb(gint source, gpointer user_data);
119 static int sync_pipe_wait_for_child(int fork_child, gchar **msgp);
120 static void pipe_convert_header(const guchar *header, int header_len, char *indicator, int *block_len);
121 static ssize_t pipe_read_block(int pipe_fd, char *indicator, int len, char *msg,
124 static void (*fetch_dumpcap_pid)(int) = NULL;
128 capture_session_init(capture_session *cap_session, void *cf)
130 cap_session->cf = cf;
131 cap_session->fork_child = -1; /* invalid process handle */
133 cap_session->signal_pipe_write_fd = -1;
135 cap_session->state = CAPTURE_STOPPED;
137 cap_session->owner = getuid();
138 cap_session->group = getgid();
140 cap_session->session_started = FALSE;
143 /* Append an arg (realloc) to an argc/argv array */
144 /* (add a string pointer to a NULL-terminated array of string pointers) */
146 sync_pipe_add_arg(char **args, int *argc, const char *arg)
148 /* Grow the array; "*argc" currently contains the number of string
149 pointers, *not* counting the NULL pointer at the end, so we have
150 to add 2 in order to get the new size of the array, including the
151 new pointer and the terminating NULL pointer. */
152 args = (char **)g_realloc( (gpointer) args, (*argc + 2) * sizeof (char *));
154 /* Stuff the pointer into the penultimate element of the array, which
155 is the one at the index specified by "*argc". */
156 args[*argc] = g_strdup(arg);
157 /* Now bump the count. */
160 /* We overwrite the NULL pointer; put it back right after the
170 /* Quote the argument element if necessary, so that it will get
171 * reconstructed correctly in the C runtime startup code. Note that
172 * the unquoting algorithm in the C runtime is really weird, and
173 * rather different than what Unix shells do. See stdargv.c in the C
174 * runtime sources (in the Platform SDK, in src/crt).
176 * Stolen from GLib's protect_argv(), an internal routine that quotes
177 * string in an argument list so that they arguments will be handled
178 * correctly in the command-line string passed to CreateProcess()
179 * if that string is constructed by gluing those strings together.
182 protect_arg (const gchar *argv)
185 const gchar *p = argv;
188 gboolean need_dblquotes = FALSE;
191 if (*p == ' ' || *p == '\t')
192 need_dblquotes = TRUE;
195 else if (*p == '\\') {
198 while (*pp && *pp == '\\')
207 q = new_arg = g_malloc (len + need_dblquotes*2 + 1);
216 else if (*p == '\\') {
219 while (*pp && *pp == '\\')
236 * Generate a string for a Win32 error.
238 #define ERRBUF_SIZE 1024
240 win32strerror(DWORD error)
242 static char errbuf[ERRBUF_SIZE+1];
246 FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
247 NULL, error, 0, errbuf, ERRBUF_SIZE, NULL);
250 * "FormatMessage()" "helpfully" sticks CR/LF at the end of the
251 * message. Get rid of it.
253 errlen = strlen(errbuf);
255 errbuf[errlen - 1] = '\0';
256 errbuf[errlen - 2] = '\0';
258 p = strchr(errbuf, '\0');
259 g_snprintf(p, (gulong)(sizeof errbuf - (p-errbuf)), " (%lu)", error);
264 * Generate a string for a Win32 exception code.
267 win32strexception(DWORD exception)
269 static char errbuf[ERRBUF_SIZE+1];
270 static const struct exception_msg {
274 { EXCEPTION_ACCESS_VIOLATION, "Access violation" },
275 { EXCEPTION_ARRAY_BOUNDS_EXCEEDED, "Array bounds exceeded" },
276 { EXCEPTION_BREAKPOINT, "Breakpoint" },
277 { EXCEPTION_DATATYPE_MISALIGNMENT, "Data type misalignment" },
278 { EXCEPTION_FLT_DENORMAL_OPERAND, "Denormal floating-point operand" },
279 { EXCEPTION_FLT_DIVIDE_BY_ZERO, "Floating-point divide by zero" },
280 { EXCEPTION_FLT_INEXACT_RESULT, "Floating-point inexact result" },
281 { EXCEPTION_FLT_INVALID_OPERATION, "Invalid floating-point operation" },
282 { EXCEPTION_FLT_OVERFLOW, "Floating-point overflow" },
283 { EXCEPTION_FLT_STACK_CHECK, "Floating-point stack check" },
284 { EXCEPTION_FLT_UNDERFLOW, "Floating-point underflow" },
285 { EXCEPTION_GUARD_PAGE, "Guard page violation" },
286 { EXCEPTION_ILLEGAL_INSTRUCTION, "Illegal instruction" },
287 { EXCEPTION_IN_PAGE_ERROR, "Page-in error" },
288 { EXCEPTION_INT_DIVIDE_BY_ZERO, "Integer divide by zero" },
289 { EXCEPTION_INT_OVERFLOW, "Integer overflow" },
290 { EXCEPTION_INVALID_DISPOSITION, "Invalid disposition" },
291 { EXCEPTION_INVALID_HANDLE, "Invalid handle" },
292 { EXCEPTION_NONCONTINUABLE_EXCEPTION, "Non-continuable exception" },
293 { EXCEPTION_PRIV_INSTRUCTION, "Privileged instruction" },
294 { EXCEPTION_SINGLE_STEP, "Single-step complete" },
295 { EXCEPTION_STACK_OVERFLOW, "Stack overflow" },
298 #define N_EXCEPTIONS (sizeof exceptions / sizeof exceptions[0])
301 for (i = 0; i < N_EXCEPTIONS; i++) {
302 if (exceptions[i].code == exception)
303 return exceptions[i].msg;
305 g_snprintf(errbuf, (gulong)sizeof errbuf, "Exception 0x%08x", exception);
310 /* Initialize an argument list and add dumpcap to it. */
312 init_pipe_args(int *argc) {
314 const char *progfile_dir;
317 progfile_dir = get_progfile_dir();
318 if (progfile_dir == NULL) {
322 /* Allocate the string pointer array with enough space for the
323 terminating NULL pointer. */
325 argv = (char **)g_malloc(sizeof (char *));
328 /* take Wireshark's absolute program path and replace "Wireshark" with "dumpcap" */
329 exename = g_strdup_printf("%s" G_DIR_SEPARATOR_S "dumpcap", progfile_dir);
331 /* Make that the first argument in the argument list (argv[0]). */
332 argv = sync_pipe_add_arg(argv, argc, exename);
334 /* sync_pipe_add_arg strdupes exename, so we should free our copy */
340 #define ARGV_NUMBER_LEN 24
341 /* a new capture run: start a new dumpcap task and hand over parameters through command line */
343 sync_pipe_start(capture_options *capture_opts, capture_session *cap_session, void (*update_cb)(void))
345 char ssnap[ARGV_NUMBER_LEN];
346 char scount[ARGV_NUMBER_LEN];
347 char sfilesize[ARGV_NUMBER_LEN];
348 char sfile_duration[ARGV_NUMBER_LEN];
349 char sring_num_files[ARGV_NUMBER_LEN];
350 char sautostop_files[ARGV_NUMBER_LEN];
351 char sautostop_filesize[ARGV_NUMBER_LEN];
352 char sautostop_duration[ARGV_NUMBER_LEN];
353 #ifdef HAVE_PCAP_REMOTE
356 #ifdef HAVE_PCAP_SETSAMPLING
357 char ssampling[ARGV_NUMBER_LEN];
360 #if defined(_WIN32) || defined(HAVE_PCAP_CREATE)
361 char buffer_size[ARGV_NUMBER_LEN];
365 HANDLE sync_pipe_read; /* pipe used to send messages from child to parent */
366 HANDLE sync_pipe_write; /* pipe used to send messages from child to parent */
367 HANDLE signal_pipe; /* named pipe used to send messages from parent to child (currently only stop) */
368 GString *args = g_string_sized_new(200);
370 SECURITY_ATTRIBUTES sa;
372 PROCESS_INFORMATION pi;
373 char control_id[ARGV_NUMBER_LEN];
374 gchar *signal_pipe_name;
377 int sync_pipe[2]; /* pipe used to send messages from child to parent */
378 enum PIPES { PIPE_READ, PIPE_WRITE }; /* Constants 0 and 1 for PIPE_READ and PIPE_WRITE */
380 int sync_pipe_read_fd;
385 interface_options interface_opts;
387 if (capture_opts->ifaces->len > 1)
388 capture_opts->use_pcapng = TRUE;
389 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_start");
390 capture_opts_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, capture_opts);
392 cap_session->fork_child = -1;
394 argv = init_pipe_args(&argc);
396 /* We don't know where to find dumpcap. */
397 report_failure("We don't know where to find dumpcap.");
401 if (capture_opts->ifaces->len > 1)
402 argv = sync_pipe_add_arg(argv, &argc, "-t");
404 if (capture_opts->use_pcapng)
405 argv = sync_pipe_add_arg(argv, &argc, "-n");
407 argv = sync_pipe_add_arg(argv, &argc, "-P");
409 if (capture_opts->capture_comment) {
410 argv = sync_pipe_add_arg(argv, &argc, "--capture-comment");
411 argv = sync_pipe_add_arg(argv, &argc, capture_opts->capture_comment);
414 if (capture_opts->multi_files_on) {
415 if (capture_opts->has_autostop_filesize) {
416 argv = sync_pipe_add_arg(argv, &argc, "-b");
417 g_snprintf(sfilesize, ARGV_NUMBER_LEN, "filesize:%u",capture_opts->autostop_filesize);
418 argv = sync_pipe_add_arg(argv, &argc, sfilesize);
421 if (capture_opts->has_file_duration) {
422 argv = sync_pipe_add_arg(argv, &argc, "-b");
423 g_snprintf(sfile_duration, ARGV_NUMBER_LEN, "duration:%d",capture_opts->file_duration);
424 argv = sync_pipe_add_arg(argv, &argc, sfile_duration);
427 if (capture_opts->has_ring_num_files) {
428 argv = sync_pipe_add_arg(argv, &argc, "-b");
429 g_snprintf(sring_num_files, ARGV_NUMBER_LEN, "files:%d",capture_opts->ring_num_files);
430 argv = sync_pipe_add_arg(argv, &argc, sring_num_files);
433 if (capture_opts->has_autostop_files) {
434 argv = sync_pipe_add_arg(argv, &argc, "-a");
435 g_snprintf(sautostop_files, ARGV_NUMBER_LEN, "files:%d",capture_opts->autostop_files);
436 argv = sync_pipe_add_arg(argv, &argc, sautostop_files);
439 if (capture_opts->has_autostop_filesize) {
440 argv = sync_pipe_add_arg(argv, &argc, "-a");
441 g_snprintf(sautostop_filesize, ARGV_NUMBER_LEN, "filesize:%u",capture_opts->autostop_filesize);
442 argv = sync_pipe_add_arg(argv, &argc, sautostop_filesize);
446 if (capture_opts->has_autostop_packets) {
447 argv = sync_pipe_add_arg(argv, &argc, "-c");
448 g_snprintf(scount, ARGV_NUMBER_LEN, "%d",capture_opts->autostop_packets);
449 argv = sync_pipe_add_arg(argv, &argc, scount);
452 if (capture_opts->has_autostop_duration) {
453 argv = sync_pipe_add_arg(argv, &argc, "-a");
454 g_snprintf(sautostop_duration, ARGV_NUMBER_LEN, "duration:%d",capture_opts->autostop_duration);
455 argv = sync_pipe_add_arg(argv, &argc, sautostop_duration);
458 if (capture_opts->group_read_access) {
459 argv = sync_pipe_add_arg(argv, &argc, "-g");
462 for (j = 0; j < capture_opts->ifaces->len; j++) {
463 interface_opts = g_array_index(capture_opts->ifaces, interface_options, j);
465 argv = sync_pipe_add_arg(argv, &argc, "-i");
466 argv = sync_pipe_add_arg(argv, &argc, interface_opts.name);
468 if (interface_opts.cfilter != NULL && strlen(interface_opts.cfilter) != 0) {
469 argv = sync_pipe_add_arg(argv, &argc, "-f");
470 argv = sync_pipe_add_arg(argv, &argc, interface_opts.cfilter);
472 if (interface_opts.snaplen != WTAP_MAX_PACKET_SIZE) {
473 argv = sync_pipe_add_arg(argv, &argc, "-s");
474 g_snprintf(ssnap, ARGV_NUMBER_LEN, "%d", interface_opts.snaplen);
475 argv = sync_pipe_add_arg(argv, &argc, ssnap);
478 if (interface_opts.linktype != -1) {
479 argv = sync_pipe_add_arg(argv, &argc, "-y");
480 argv = sync_pipe_add_arg(argv, &argc, linktype_val_to_name(interface_opts.linktype));
483 if (!interface_opts.promisc_mode) {
484 argv = sync_pipe_add_arg(argv, &argc, "-p");
487 #if defined(_WIN32) || defined(HAVE_PCAP_CREATE)
488 if (interface_opts.buffer_size != DEFAULT_CAPTURE_BUFFER_SIZE) {
489 argv = sync_pipe_add_arg(argv, &argc, "-B");
490 g_snprintf(buffer_size, ARGV_NUMBER_LEN, "%d", interface_opts.buffer_size);
491 argv = sync_pipe_add_arg(argv, &argc, buffer_size);
495 #ifdef HAVE_PCAP_CREATE
496 if (interface_opts.monitor_mode) {
497 argv = sync_pipe_add_arg(argv, &argc, "-I");
501 #ifdef HAVE_PCAP_REMOTE
502 if (interface_opts.datatx_udp)
503 argv = sync_pipe_add_arg(argv, &argc, "-u");
505 if (!interface_opts.nocap_rpcap)
506 argv = sync_pipe_add_arg(argv, &argc, "-r");
508 if (interface_opts.auth_type == CAPTURE_AUTH_PWD) {
509 argv = sync_pipe_add_arg(argv, &argc, "-A");
510 g_snprintf(sauth, sizeof(sauth), "%s:%s",
511 interface_opts.auth_username,
512 interface_opts.auth_password);
513 argv = sync_pipe_add_arg(argv, &argc, sauth);
517 #ifdef HAVE_PCAP_SETSAMPLING
518 if (interface_opts.sampling_method != CAPTURE_SAMP_NONE) {
519 argv = sync_pipe_add_arg(argv, &argc, "-m");
520 g_snprintf(ssampling, ARGV_NUMBER_LEN, "%s:%d",
521 interface_opts.sampling_method == CAPTURE_SAMP_BY_COUNT ? "count" :
522 interface_opts.sampling_method == CAPTURE_SAMP_BY_TIMER ? "timer" :
524 interface_opts.sampling_param);
525 argv = sync_pipe_add_arg(argv, &argc, ssampling);
530 /* dumpcap should be running in capture child mode (hidden feature) */
532 argv = sync_pipe_add_arg(argv, &argc, "-Z");
534 g_snprintf(control_id, ARGV_NUMBER_LEN, "%d", GetCurrentProcessId());
535 argv = sync_pipe_add_arg(argv, &argc, control_id);
537 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
541 if (capture_opts->save_file) {
542 argv = sync_pipe_add_arg(argv, &argc, "-w");
543 argv = sync_pipe_add_arg(argv, &argc, capture_opts->save_file);
545 for (i = 0; i < argc; i++) {
546 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "argv[%d]: %s", i, argv[i]);
550 /* init SECURITY_ATTRIBUTES */
551 sa.nLength = sizeof(SECURITY_ATTRIBUTES);
552 sa.bInheritHandle = TRUE;
553 sa.lpSecurityDescriptor = NULL;
555 /* Create a pipe for the child process */
556 /* (increase this value if you have trouble while fast capture file switches) */
557 if (! CreatePipe(&sync_pipe_read, &sync_pipe_write, &sa, 5120)) {
558 /* Couldn't create the pipe between parent and child. */
559 report_failure("Couldn't create sync pipe: %s",
560 win32strerror(GetLastError()));
561 for (i = 0; i < argc; i++) {
562 g_free( (gpointer) argv[i]);
564 g_free( (gpointer) argv);
568 /* Create the signal pipe */
569 signal_pipe_name = g_strdup_printf(SIGNAL_PIPE_FORMAT, control_id);
570 signal_pipe = CreateNamedPipe(utf_8to16(signal_pipe_name),
571 PIPE_ACCESS_OUTBOUND, PIPE_TYPE_BYTE, 1, 65535, 65535, 0, NULL);
572 g_free(signal_pipe_name);
574 if (signal_pipe == INVALID_HANDLE_VALUE) {
575 /* Couldn't create the signal pipe between parent and child. */
576 report_failure("Couldn't create signal pipe: %s",
577 win32strerror(GetLastError()));
578 for (i = 0; i < argc; i++) {
579 g_free( (gpointer) argv[i]);
581 g_free( (gpointer) argv);
585 /* init STARTUPINFO */
586 memset(&si, 0, sizeof(si));
589 si.dwFlags = STARTF_USESHOWWINDOW;
590 si.wShowWindow = SW_SHOW;
592 si.dwFlags = STARTF_USESTDHANDLES|STARTF_USESHOWWINDOW;
593 si.wShowWindow = SW_HIDE; /* this hides the console window */
594 si.hStdInput = GetStdHandle(STD_INPUT_HANDLE);
595 si.hStdOutput = GetStdHandle(STD_OUTPUT_HANDLE);
596 si.hStdError = sync_pipe_write;
597 /*si.hStdError = (HANDLE) _get_osfhandle(2);*/
600 /* convert args array into a single string */
601 /* XXX - could change sync_pipe_add_arg() instead */
602 /* there is a drawback here: the length is internally limited to 1024 bytes */
603 for(i=0; argv[i] != 0; i++) {
604 if(i != 0) g_string_append_c(args, ' '); /* don't prepend a space before the path!!! */
605 quoted_arg = protect_arg(argv[i]);
606 g_string_append(args, quoted_arg);
611 if(!CreateProcess(NULL, utf_8to16(args->str), NULL, NULL, TRUE,
612 CREATE_NEW_CONSOLE, NULL, NULL, &si, &pi)) {
613 report_failure("Couldn't run %s in child process: %s",
614 args->str, win32strerror(GetLastError()));
615 CloseHandle(sync_pipe_read);
616 CloseHandle(sync_pipe_write);
617 for (i = 0; i < argc; i++) {
618 g_free( (gpointer) argv[i]);
620 g_free( (gpointer) argv);
623 cap_session->fork_child = (int) pi.hProcess;
624 g_string_free(args, TRUE);
626 /* associate the operating system filehandle to a C run-time file handle */
627 /* (good file handle infos at: http://www.flounder.com/handles.htm) */
628 sync_pipe_read_fd = _open_osfhandle( (long) sync_pipe_read, _O_BINARY);
630 /* associate the operating system filehandle to a C run-time file handle */
631 cap_session->signal_pipe_write_fd = _open_osfhandle( (long) signal_pipe, _O_BINARY);
634 if (pipe(sync_pipe) < 0) {
635 /* Couldn't create the pipe between parent and child. */
636 report_failure("Couldn't create sync pipe: %s", g_strerror(errno));
637 for (i = 0; i < argc; i++) {
638 g_free( (gpointer) argv[i]);
644 if ((cap_session->fork_child = fork()) == 0) {
646 * Child process - run dumpcap with the right arguments to make
647 * it just capture with the specified capture parameters
649 dup2(sync_pipe[PIPE_WRITE], 2);
650 ws_close(sync_pipe[PIPE_READ]);
651 execv(argv[0], argv);
652 g_snprintf(errmsg, sizeof errmsg, "Couldn't run %s in child process: %s",
653 argv[0], g_strerror(errno));
654 sync_pipe_errmsg_to_parent(2, errmsg, "");
656 /* Exit with "_exit()", so that we don't close the connection
657 to the X server (and cause stuff buffered up by our parent but
658 not yet sent to be sent, as that stuff should only be sent by
659 our parent). We've sent an error message to the parent, so
660 we exit with an exit status of 1 (any exit status other than
661 0 or 1 will cause an additional message to report that exit
662 status, over and above the error message we sent to the parent). */
666 if (fetch_dumpcap_pid && cap_session->fork_child > 0)
667 fetch_dumpcap_pid(cap_session->fork_child);
669 sync_pipe_read_fd = sync_pipe[PIPE_READ];
672 for (i = 0; i < argc; i++) {
673 g_free( (gpointer) argv[i]);
676 /* Parent process - read messages from the child process over the
678 g_free( (gpointer) argv); /* free up arg array */
680 /* Close the write side of the pipe, so that only the child has it
681 open, and thus it completely closes, and thus returns to us
682 an EOF indication, if the child closes it (either deliberately
683 or by exiting abnormally). */
685 CloseHandle(sync_pipe_write);
687 ws_close(sync_pipe[PIPE_WRITE]);
690 if (cap_session->fork_child == -1) {
691 /* We couldn't even create the child process. */
692 report_failure("Couldn't create child process: %s", g_strerror(errno));
693 ws_close(sync_pipe_read_fd);
695 ws_close(cap_session->signal_pipe_write_fd);
700 cap_session->fork_child_status = 0;
701 cap_session->capture_opts = capture_opts;
703 /* we might wait for a moment till child is ready, so update screen now */
704 if (update_cb) update_cb();
706 /* We were able to set up to read the capture file;
707 arrange that our callback be called whenever it's possible
708 to read from the sync pipe, so that it's called when
709 the child process wants to tell us something. */
711 /* we have a running capture, now wait for the real capture filename */
712 pipe_input_set_handler(sync_pipe_read_fd, (gpointer) cap_session,
713 &cap_session->fork_child, sync_pipe_input_cb);
719 * Open two pipes to dumpcap with the supplied arguments, one for its
720 * standard output and one for its standard error.
722 * On success, *msg is unchanged and 0 is returned; data_read_fd,
723 * messsage_read_fd, and fork_child point to the standard output pipe's
724 * file descriptor, the standard error pipe's file descriptor, and
725 * the child's PID/handle, respectively.
727 * On failure, *msg points to an error message for the failure, and -1 is
728 * returned, in which case *msg must be freed with g_free().
730 /* XXX - This duplicates a lot of code in sync_pipe_start() */
731 /* XXX - assumes PIPE_BUF_SIZE > SP_MAX_MSG_LEN */
732 #define PIPE_BUF_SIZE 5120
734 sync_pipe_open_command(char** argv, int *data_read_fd,
735 int *message_read_fd, int *fork_child, gchar **msg, void(*update_cb)(void))
737 enum PIPES { PIPE_READ, PIPE_WRITE }; /* Constants 0 and 1 for PIPE_READ and PIPE_WRITE */
739 HANDLE sync_pipe[2]; /* pipe used to send messages from child to parent */
740 HANDLE data_pipe[2]; /* pipe used to send data from child to parent */
741 GString *args = g_string_sized_new(200);
743 SECURITY_ATTRIBUTES sa;
745 PROCESS_INFORMATION pi;
748 int sync_pipe[2]; /* pipe used to send messages from child to parent */
749 int data_pipe[2]; /* pipe used to send data from child to parent */
754 *message_read_fd = -1;
755 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_open_command");
758 /* We can't return anything */
760 g_string_free(args, TRUE);
766 /* init SECURITY_ATTRIBUTES */
767 sa.nLength = sizeof(SECURITY_ATTRIBUTES);
768 sa.bInheritHandle = TRUE;
769 sa.lpSecurityDescriptor = NULL;
771 /* Create a pipe for the child process to send us messages */
772 /* (increase this value if you have trouble while fast capture file switches) */
773 if (! CreatePipe(&sync_pipe[PIPE_READ], &sync_pipe[PIPE_WRITE], &sa, 5120)) {
774 /* Couldn't create the message pipe between parent and child. */
775 *msg = g_strdup_printf("Couldn't create sync pipe: %s",
776 win32strerror(GetLastError()));
777 for (i = 0; argv[i] != NULL; i++) {
778 g_free( (gpointer) argv[i]);
780 g_free( (gpointer) argv);
784 /* Create a pipe for the child process to send us data */
785 /* (increase this value if you have trouble while fast capture file switches) */
786 if (! CreatePipe(&data_pipe[PIPE_READ], &data_pipe[PIPE_WRITE], &sa, 5120)) {
787 /* Couldn't create the message pipe between parent and child. */
788 *msg = g_strdup_printf("Couldn't create data pipe: %s",
789 win32strerror(GetLastError()));
790 CloseHandle(sync_pipe[PIPE_READ]);
791 CloseHandle(sync_pipe[PIPE_WRITE]);
792 for (i = 0; argv[i] != NULL; i++) {
793 g_free( (gpointer) argv[i]);
795 g_free( (gpointer) argv);
799 /* init STARTUPINFO */
800 memset(&si, 0, sizeof(si));
803 si.dwFlags = STARTF_USESHOWWINDOW;
804 si.wShowWindow = SW_SHOW;
806 si.dwFlags = STARTF_USESTDHANDLES|STARTF_USESHOWWINDOW;
807 si.wShowWindow = SW_HIDE; /* this hides the console window */
809 si.hStdOutput = data_pipe[PIPE_WRITE];
810 si.hStdError = sync_pipe[PIPE_WRITE];
813 /* convert args array into a single string */
814 /* XXX - could change sync_pipe_add_arg() instead */
815 /* there is a drawback here: the length is internally limited to 1024 bytes */
816 for(i=0; argv[i] != 0; i++) {
817 if(i != 0) g_string_append_c(args, ' '); /* don't prepend a space before the path!!! */
818 quoted_arg = protect_arg(argv[i]);
819 g_string_append(args, quoted_arg);
824 if(!CreateProcess(NULL, utf_8to16(args->str), NULL, NULL, TRUE,
825 CREATE_NEW_CONSOLE, NULL, NULL, &si, &pi)) {
826 *msg = g_strdup_printf("Couldn't run %s in child process: %s",
827 args->str, win32strerror(GetLastError()));
828 CloseHandle(data_pipe[PIPE_READ]);
829 CloseHandle(data_pipe[PIPE_WRITE]);
830 CloseHandle(sync_pipe[PIPE_READ]);
831 CloseHandle(sync_pipe[PIPE_WRITE]);
832 for (i = 0; argv[i] != NULL; i++) {
833 g_free( (gpointer) argv[i]);
835 g_free( (gpointer) argv);
838 *fork_child = (int) pi.hProcess;
839 g_string_free(args, TRUE);
841 /* associate the operating system filehandles to C run-time file handles */
842 /* (good file handle infos at: http://www.flounder.com/handles.htm) */
843 *data_read_fd = _open_osfhandle( (long) data_pipe[PIPE_READ], _O_BINARY);
844 *message_read_fd = _open_osfhandle( (long) sync_pipe[PIPE_READ], _O_BINARY);
846 /* Create a pipe for the child process to send us messages */
847 if (pipe(sync_pipe) < 0) {
848 /* Couldn't create the message pipe between parent and child. */
849 *msg = g_strdup_printf("Couldn't create sync pipe: %s", g_strerror(errno));
850 for (i = 0; argv[i] != NULL; i++) {
851 g_free( (gpointer) argv[i]);
857 /* Create a pipe for the child process to send us data */
858 if (pipe(data_pipe) < 0) {
859 /* Couldn't create the data pipe between parent and child. */
860 *msg = g_strdup_printf("Couldn't create data pipe: %s", g_strerror(errno));
861 ws_close(sync_pipe[PIPE_READ]);
862 ws_close(sync_pipe[PIPE_WRITE]);
863 for (i = 0; argv[i] != NULL; i++) {
864 g_free( (gpointer) argv[i]);
870 if ((*fork_child = fork()) == 0) {
872 * Child process - run dumpcap with the right arguments to make
873 * it just capture with the specified capture parameters
875 dup2(data_pipe[PIPE_WRITE], 1);
876 ws_close(data_pipe[PIPE_READ]);
877 ws_close(data_pipe[PIPE_WRITE]);
878 dup2(sync_pipe[PIPE_WRITE], 2);
879 ws_close(sync_pipe[PIPE_READ]);
880 ws_close(sync_pipe[PIPE_WRITE]);
881 execv(argv[0], argv);
882 g_snprintf(errmsg, sizeof errmsg, "Couldn't run %s in child process: %s",
883 argv[0], g_strerror(errno));
884 sync_pipe_errmsg_to_parent(2, errmsg, "");
886 /* Exit with "_exit()", so that we don't close the connection
887 to the X server (and cause stuff buffered up by our parent but
888 not yet sent to be sent, as that stuff should only be sent by
889 our parent). We've sent an error message to the parent, so
890 we exit with an exit status of 1 (any exit status other than
891 0 or 1 will cause an additional message to report that exit
892 status, over and above the error message we sent to the parent). */
896 if (fetch_dumpcap_pid && *fork_child > 0)
897 fetch_dumpcap_pid(*fork_child);
899 *data_read_fd = data_pipe[PIPE_READ];
900 *message_read_fd = sync_pipe[PIPE_READ];
903 for (i = 0; argv[i] != NULL; i++) {
904 g_free( (gpointer) argv[i]);
907 /* Parent process - read messages from the child process over the
909 g_free( (gpointer) argv); /* free up arg array */
911 /* Close the write sides of the pipes, so that only the child has them
912 open, and thus they completely close, and thus return to us
913 an EOF indication, if the child closes them (either deliberately
914 or by exiting abnormally). */
916 CloseHandle(data_pipe[PIPE_WRITE]);
917 CloseHandle(sync_pipe[PIPE_WRITE]);
919 ws_close(data_pipe[PIPE_WRITE]);
920 ws_close(sync_pipe[PIPE_WRITE]);
923 if (*fork_child == -1) {
924 /* We couldn't even create the child process. */
925 *msg = g_strdup_printf("Couldn't create child process: %s", g_strerror(errno));
926 ws_close(*data_read_fd);
927 ws_close(*message_read_fd);
931 /* we might wait for a moment till child is ready, so update screen now */
932 if (update_cb) update_cb();
937 * Close the pipes we're using to read from dumpcap, and wait for it
938 * to exit. On success, *msgp is unchanged, and the exit status of
939 * dumpcap is returned. On failure (which includes "dumpcap exited
940 * due to being killed by a signal or an exception"), *msgp points
941 * to an error message for the failure, and -1 is returned. In the
942 * latter case, *msgp must be freed with g_free().
945 sync_pipe_close_command(int *data_read_fd, int *message_read_fd,
946 int *fork_child, gchar **msgp)
948 ws_close(*data_read_fd);
949 if (message_read_fd != NULL)
950 ws_close(*message_read_fd);
953 /* XXX - Should we signal the child somehow? */
954 sync_pipe_kill(*fork_child);
957 return sync_pipe_wait_for_child(*fork_child, msgp);
961 * Run dumpcap with the supplied arguments.
963 * On success, *data points to a buffer containing the dumpcap output,
964 * *primary_msg and *secondary_message are NULL, and 0 is returned; *data
965 * must be freed with g_free().
967 * On failure, *data is NULL, *primary_msg points to an error message,
968 * *secondary_msg either points to an additional error message or is
969 * NULL, and -1 is returned; *primary_msg, and *secondary_msg if not NULL,
970 * must be freed with g_free().
972 /* XXX - This duplicates a lot of code in sync_pipe_start() */
973 /* XXX - assumes PIPE_BUF_SIZE > SP_MAX_MSG_LEN */
974 #define PIPE_BUF_SIZE 5120
976 sync_pipe_run_command_actual(char** argv, gchar **data, gchar **primary_msg,
977 gchar **secondary_msg, void(*update_cb)(void))
980 int data_pipe_read_fd, sync_pipe_read_fd, fork_child, ret;
982 gchar buffer[PIPE_BUF_SIZE+1] = {0};
986 char *primary_msg_text;
987 int secondary_msg_len;
988 char *secondary_msg_text;
990 GString *data_buf = NULL;
993 ret = sync_pipe_open_command(argv, &data_pipe_read_fd, &sync_pipe_read_fd,
994 &fork_child, &msg, update_cb);
997 *secondary_msg = NULL;
1003 * We were able to set up to read dumpcap's output. Do so.
1005 * First, wait for an SP_ERROR_MSG message or SP_SUCCESS message.
1007 nread = pipe_read_block(sync_pipe_read_fd, &indicator, SP_MAX_MSG_LEN,
1008 buffer, primary_msg);
1010 /* We got a read error from the sync pipe, or we got no data at
1011 all from the sync pipe, so we're not going to be getting any
1012 data or error message from the child process. Pick up its
1013 exit status, and complain.
1015 We don't have to worry about killing the child, if the sync pipe
1016 returned an error. Usually this error is caused as the child killed
1017 itself while going down. Even in the rare cases that this isn't the
1018 case, the child will get an error when writing to the broken pipe
1019 the next time, cleaning itself up then. */
1020 ret = sync_pipe_wait_for_child(fork_child, &wait_msg);
1022 /* We got an EOF from the sync pipe. That means that it exited
1023 before giving us any data to read. If ret is -1, we report
1024 that as a bad exit (e.g., exiting due to a signal); otherwise,
1025 we report it as a premature exit. */
1027 *primary_msg = wait_msg;
1029 *primary_msg = g_strdup("Child dumpcap closed sync pipe prematurely");
1031 /* We got an error from the sync pipe. If ret is -1, report
1032 both the sync pipe I/O error and the wait error. */
1034 combined_msg = g_strdup_printf("%s\n\n%s", *primary_msg, wait_msg);
1035 g_free(*primary_msg);
1037 *primary_msg = combined_msg;
1040 *secondary_msg = NULL;
1045 /* we got a valid message block from the child, process it */
1050 * Error from dumpcap; there will be a primary message and a
1051 * secondary message.
1054 /* convert primary message */
1055 pipe_convert_header((guchar*)buffer, 4, &indicator, &primary_msg_len);
1056 primary_msg_text = buffer+4;
1057 /* convert secondary message */
1058 pipe_convert_header((guchar*)primary_msg_text + primary_msg_len, 4, &indicator,
1059 &secondary_msg_len);
1060 secondary_msg_text = primary_msg_text + primary_msg_len + 4;
1061 /* the capture child will close the sync_pipe, nothing to do */
1064 * Pick up the child status.
1066 ret = sync_pipe_close_command(&data_pipe_read_fd, &sync_pipe_read_fd,
1070 * Child process failed unexpectedly, or wait failed; msg is the
1074 *secondary_msg = NULL;
1077 * Child process failed, but returned the expected exit status.
1078 * Return the messages it gave us, and indicate failure.
1080 *primary_msg = g_strdup(primary_msg_text);
1081 *secondary_msg = g_strdup(secondary_msg_text);
1088 /* read the output from the command */
1089 data_buf = g_string_new("");
1090 while ((count = ws_read(data_pipe_read_fd, buffer, PIPE_BUF_SIZE)) > 0) {
1091 buffer[count] = '\0';
1092 g_string_append(data_buf, buffer);
1096 * Pick up the child status.
1098 ret = sync_pipe_close_command(&data_pipe_read_fd, &sync_pipe_read_fd,
1102 * Child process failed unexpectedly, or wait failed; msg is the
1106 *secondary_msg = NULL;
1107 g_string_free(data_buf, TRUE);
1111 * Child process succeeded.
1113 *primary_msg = NULL;
1114 *secondary_msg = NULL;
1115 *data = data_buf->str;
1116 g_string_free(data_buf, FALSE);
1122 * Pick up the child status.
1124 ret = sync_pipe_close_command(&data_pipe_read_fd, &sync_pipe_read_fd,
1128 * Child process failed unexpectedly, or wait failed; msg is the
1132 *secondary_msg = NULL;
1135 * Child process returned an unknown status.
1137 *primary_msg = g_strdup_printf("dumpcap process gave an unexpected message type: 0x%02x",
1139 *secondary_msg = NULL;
1148 /* centralised logging and timing for sync_pipe_run_command_actual(),
1149 * redirects to sync_pipe_run_command_actual()
1152 sync_pipe_run_command(char** argv, gchar **data, gchar **primary_msg,
1153 gchar **secondary_msg, void (*update_cb)(void))
1156 GTimeVal start_time;
1159 int logging_enabled;
1161 /* check if logging is actually enabled, otherwise don't expend the CPU generating logging */
1162 logging_enabled=( (G_LOG_LEVEL_DEBUG | G_LOG_LEVEL_INFO) & G_LOG_LEVEL_MASK & prefs.console_log_level);
1163 if(logging_enabled){
1164 g_get_current_time(&start_time);
1165 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_INFO, "sync_pipe_run_command() starts");
1166 for(i=0; argv[i] != 0; i++) {
1167 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, " argv[%d]: %s", i, argv[i]);
1170 /* do the actual sync pipe run command */
1171 ret=sync_pipe_run_command_actual(argv, data, primary_msg, secondary_msg, update_cb);
1173 if(logging_enabled){
1174 g_get_current_time(&end_time);
1175 elapsed = (float) ((end_time.tv_sec - start_time.tv_sec) +
1176 ((end_time.tv_usec - start_time.tv_usec) / 1e6));
1178 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_INFO, "sync_pipe_run_command() ends, taking %.3fs, result=%d", elapsed, ret);
1186 sync_interface_set_80211_chan(const gchar *iface, const char *freq, const gchar *type,
1187 gchar **data, gchar **primary_msg,
1188 gchar **secondary_msg, void (*update_cb)(void))
1194 argv = init_pipe_args(&argc);
1197 *primary_msg = g_strdup("We don't know where to find dumpcap.");
1198 *secondary_msg = NULL;
1203 argv = sync_pipe_add_arg(argv, &argc, "-i");
1204 argv = sync_pipe_add_arg(argv, &argc, iface);
1207 opt = g_strdup_printf("%s,%s", freq, type);
1209 opt = g_strdup_printf("%s", freq);
1212 *primary_msg = g_strdup("Out of mem.");
1213 *secondary_msg = NULL;
1218 argv = sync_pipe_add_arg(argv, &argc, "-k");
1219 argv = sync_pipe_add_arg(argv, &argc, opt);
1222 /* Run dumpcap in capture child mode */
1223 argv = sync_pipe_add_arg(argv, &argc, "-Z");
1224 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
1227 ret = sync_pipe_run_command(argv, data, primary_msg, secondary_msg, update_cb);
1233 * Get the list of interfaces using dumpcap.
1235 * On success, *data points to a buffer containing the dumpcap output,
1236 * *primary_msg and *secondary_msg are NULL, and 0 is returned. *data
1237 * must be freed with g_free().
1239 * On failure, *data is NULL, *primary_msg points to an error message,
1240 * *secondary_msg either points to an additional error message or is
1241 * NULL, and -1 is returned; *primary_msg, and *secondary_msg if not NULL,
1242 * must be freed with g_free().
1245 sync_interface_list_open(gchar **data, gchar **primary_msg,
1246 gchar **secondary_msg, void (*update_cb)(void))
1251 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_interface_list_open");
1253 argv = init_pipe_args(&argc);
1256 *primary_msg = g_strdup("We don't know where to find dumpcap..");
1257 *secondary_msg = NULL;
1262 /* Ask for the interface list */
1263 argv = sync_pipe_add_arg(argv, &argc, "-D");
1266 /* Run dumpcap in capture child mode */
1267 argv = sync_pipe_add_arg(argv, &argc, "-Z");
1268 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
1270 return sync_pipe_run_command(argv, data, primary_msg, secondary_msg, update_cb);
1274 * Get the capabilities of an interface using dumpcap.
1276 * On success, *data points to a buffer containing the dumpcap output,
1277 * *primary_msg and *secondary_msg are NULL, and 0 is returned. *data
1278 * must be freed with g_free().
1280 * On failure, *data is NULL, *primary_msg points to an error message,
1281 * *secondary_msg either points to an additional error message or is
1282 * NULL, and -1 is returned; *primary_msg, and *secondary_msg if not NULL,
1283 * must be freed with g_free().
1286 sync_if_capabilities_open(const gchar *ifname, gboolean monitor_mode,
1287 gchar **data, gchar **primary_msg,
1288 gchar **secondary_msg, void (*update_cb)(void))
1293 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_if_capabilities_open");
1295 argv = init_pipe_args(&argc);
1298 *primary_msg = g_strdup("We don't know where to find dumpcap.");
1299 *secondary_msg = NULL;
1304 /* Ask for the interface capabilities */
1305 argv = sync_pipe_add_arg(argv, &argc, "-i");
1306 argv = sync_pipe_add_arg(argv, &argc, ifname);
1307 argv = sync_pipe_add_arg(argv, &argc, "-L");
1309 argv = sync_pipe_add_arg(argv, &argc, "-I");
1312 /* Run dumpcap in capture child mode */
1313 argv = sync_pipe_add_arg(argv, &argc, "-Z");
1314 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
1316 return sync_pipe_run_command(argv, data, primary_msg, secondary_msg, update_cb);
1320 * Start getting interface statistics using dumpcap. On success, read_fd
1321 * contains the file descriptor for the pipe's stdout, *msg is unchanged,
1322 * and zero is returned. On failure, *msg will point to an error message
1323 * that must be g_free()d, and -1 will be returned.
1326 sync_interface_stats_open(int *data_read_fd, int *fork_child, gchar **msg, void (*update_cb)(void))
1330 int message_read_fd, ret;
1332 gchar buffer[PIPE_BUF_SIZE+1] = {0};
1335 int primary_msg_len;
1336 char *primary_msg_text;
1337 int secondary_msg_len;
1338 /*char *secondary_msg_text;*/
1341 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_interface_stats_open");
1343 argv = init_pipe_args(&argc);
1346 *msg = g_strdup("We don't know where to find dumpcap.");
1350 /* Ask for the interface statistics */
1351 argv = sync_pipe_add_arg(argv, &argc, "-S");
1354 argv = sync_pipe_add_arg(argv, &argc, "-Z");
1356 create_dummy_signal_pipe();
1357 argv = sync_pipe_add_arg(argv, &argc, dummy_control_id);
1359 argv = sync_pipe_add_arg(argv, &argc, SIGNAL_PIPE_CTRL_ID_NONE);
1362 ret = sync_pipe_open_command(argv, data_read_fd, &message_read_fd,
1363 fork_child, msg, update_cb);
1368 * We were able to set up to read dumpcap's output. Do so.
1370 * First, wait for an SP_ERROR_MSG message or SP_SUCCESS message.
1372 nread = pipe_read_block(message_read_fd, &indicator, SP_MAX_MSG_LEN,
1375 /* We got a read error from the sync pipe, or we got no data at
1376 all from the sync pipe, so we're not going to be getting any
1377 data or error message from the child process. Pick up its
1378 exit status, and complain.
1380 We don't have to worry about killing the child, if the sync pipe
1381 returned an error. Usually this error is caused as the child killed
1382 itself while going down. Even in the rare cases that this isn't the
1383 case, the child will get an error when writing to the broken pipe
1384 the next time, cleaning itself up then. */
1385 ret = sync_pipe_wait_for_child(*fork_child, &wait_msg);
1387 /* We got an EOF from the sync pipe. That means that it exited
1388 before giving us any data to read. If ret is -1, we report
1389 that as a bad exit (e.g., exiting due to a signal); otherwise,
1390 we report it as a premature exit. */
1394 *msg = g_strdup("Child dumpcap closed sync pipe prematurely");
1396 /* We got an error from the sync pipe. If ret is -1, report
1397 both the sync pipe I/O error and the wait error. */
1399 combined_msg = g_strdup_printf("%s\n\n%s", *msg, wait_msg);
1402 *msg = combined_msg;
1409 /* we got a valid message block from the child, process it */
1414 * Error from dumpcap; there will be a primary message and a
1415 * secondary message.
1418 /* convert primary message */
1419 pipe_convert_header((guchar*)buffer, 4, &indicator, &primary_msg_len);
1420 primary_msg_text = buffer+4;
1421 /* convert secondary message */
1422 pipe_convert_header((guchar*)primary_msg_text + primary_msg_len, 4, &indicator,
1423 &secondary_msg_len);
1424 /*secondary_msg_text = primary_msg_text + primary_msg_len + 4;*/
1425 /* the capture child will close the sync_pipe, nothing to do */
1428 * Pick up the child status.
1430 ret = sync_pipe_close_command(data_read_fd, &message_read_fd,
1434 * Child process failed unexpectedly, or wait failed; msg is the
1439 * Child process failed, but returned the expected exit status.
1440 * Return the messages it gave us, and indicate failure.
1442 *msg = g_strdup(primary_msg_text);
1448 /* Close the message pipe. */
1449 ws_close(message_read_fd);
1454 * Pick up the child status.
1456 ret = sync_pipe_close_command(data_read_fd, &message_read_fd,
1460 * Child process failed unexpectedly, or wait failed; msg is the
1465 * Child process returned an unknown status.
1467 *msg = g_strdup_printf("dumpcap process gave an unexpected message type: 0x%02x",
1476 /* Close down the stats process */
1478 sync_interface_stats_close(int *read_fd, int *fork_child, gchar **msg)
1482 * Don't bother waiting for the child. sync_pipe_close_command
1483 * does this for us on Windows.
1485 sync_pipe_kill(*fork_child);
1487 return sync_pipe_close_command(read_fd, NULL, fork_child, msg);
1490 /* read a number of bytes from a pipe */
1491 /* (blocks until enough bytes read or an error occurs) */
1493 pipe_read_bytes(int pipe_fd, char *bytes, int required, char **msg)
1500 newly = read(pipe_fd, &bytes[offset], required);
1503 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1504 "read from pipe %d: EOF (capture closed?)", pipe_fd);
1511 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1512 "read from pipe %d: error(%u): %s", pipe_fd, error,
1514 *msg = g_strdup_printf("Error reading from sync pipe: %s",
1519 required -= (int)newly;
1527 static gboolean pipe_data_available(int pipe_fd) {
1528 #ifdef _WIN32 /* PeekNamedPipe */
1529 HANDLE hPipe = (HANDLE) _get_osfhandle(pipe_fd);
1532 if (hPipe == INVALID_HANDLE_VALUE)
1535 if (! PeekNamedPipe(hPipe, NULL, 0, NULL, &bytes_avail, NULL))
1538 if (bytes_avail > 0)
1543 struct timeval timeout;
1546 FD_SET(pipe_fd, &rfds);
1548 timeout.tv_usec = 0;
1550 if (select(pipe_fd+1, &rfds, NULL, NULL, &timeout) > 0)
1557 /* Read a line from a pipe, similar to fgets */
1559 sync_pipe_gets_nonblock(int pipe_fd, char *bytes, int max) {
1563 while(offset < max - 1) {
1565 if (! pipe_data_available(pipe_fd))
1567 newly = read(pipe_fd, &bytes[offset], 1);
1569 /* EOF - not necessarily an error */
1571 } else if (newly == -1) {
1573 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1574 "read from pipe %d: error(%u): %s", pipe_fd, errno, g_strerror(errno));
1576 } else if (bytes[offset] == '\n') {
1582 bytes[offset] = '\0';
1588 /* convert header values (indicator and 3-byte length) */
1590 pipe_convert_header(const guchar *header, int header_len, char *indicator, int *block_len) {
1592 g_assert(header_len == 4);
1594 /* convert header values */
1595 *indicator = header[0];
1596 *block_len = (header[1]&0xFF)<<16 | (header[2]&0xFF)<<8 | (header[3]&0xFF);
1599 /* read a message from the sending pipe in the standard format
1600 (1-byte message indicator, 3-byte message length (excluding length
1601 and indicator field), and the rest is the message) */
1603 pipe_read_block(int pipe_fd, char *indicator, int len, char *msg,
1610 /* read header (indicator and 3-byte length) */
1611 newly = pipe_read_bytes(pipe_fd, header, 4, err_msg);
1615 * Immediate EOF; if the capture child exits normally, this
1616 * is an "I'm done" indication, so don't report it as an
1619 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1620 "read %d got an EOF", pipe_fd);
1623 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1624 "read %d failed to read header: %lu", pipe_fd, (long)newly);
1627 * Short read, but not an immediate EOF.
1629 *err_msg = g_strdup_printf("Premature EOF reading from sync pipe: got only %ld bytes",
1635 /* convert header values */
1636 pipe_convert_header((guchar*)header, 4, indicator, &required);
1638 /* only indicator with no value? */
1640 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1641 "read %d indicator: %c empty value", pipe_fd, *indicator);
1645 /* does the data fit into the given buffer? */
1646 if(required > len) {
1647 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1648 "read %d length error, required %d > len %d, header: 0x%02x 0x%02x 0x%02x 0x%02x",
1649 pipe_fd, required, len,
1650 header[0], header[1], header[2], header[3]);
1652 /* we have a problem here, try to read some more bytes from the pipe to debug where the problem really is */
1653 memcpy(msg, header, sizeof(header));
1654 newly = read(pipe_fd, &msg[sizeof(header)], len-sizeof(header));
1655 if (newly < 0) { /* error */
1656 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1657 "read from pipe %d: error(%u): %s", pipe_fd, errno, g_strerror(errno));
1659 *err_msg = g_strdup_printf("Unknown message from dumpcap, try to show it as a string: %s",
1665 /* read the actual block data */
1666 newly = pipe_read_bytes(pipe_fd, msg, required, err_msg);
1667 if(newly != required) {
1669 *err_msg = g_strdup_printf("Unknown message from dumpcap, try to show it as a string: %s",
1675 /* XXX If message is "2part", the msg probably won't be sent to debug log correctly */
1676 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG,
1677 "read %d ok indicator: %c len: %u msg: %s", pipe_fd, *indicator,
1684 /* There's stuff to read from the sync pipe, meaning the child has sent
1685 us a message, or the sync pipe has closed, meaning the child has
1686 closed it (perhaps because it exited). */
1688 sync_pipe_input_cb(gint source, gpointer user_data)
1690 capture_session *cap_session = (capture_session *)user_data;
1692 char buffer[SP_MAX_MSG_LEN+1] = {0};
1698 char *secondary_msg;
1699 char *wait_msg, *combined_msg;
1702 nread = pipe_read_block(source, &indicator, SP_MAX_MSG_LEN, buffer,
1705 /* We got a read error, or a bad message, or an EOF, from the sync pipe.
1707 If we got a read error or a bad message, nread is -1 and
1708 primary_msg is set to point to an error message. We don't
1709 have to worry about killing the child; usually this error
1710 is caused as the child killed itself while going down.
1711 Even in the rare cases that this isn't the case, the child
1712 will get an error when writing to the broken pipe the next time,
1713 cleaning itself up then.
1715 If we got an EOF, nread is 0 and primary_msg isn't set. This
1716 is an indication that the capture is finished. */
1717 ret = sync_pipe_wait_for_child(cap_session->fork_child, &wait_msg);
1719 /* We got an EOF from the sync pipe. That means that the capture
1720 child exited, and not in the middle of a message; we treat
1721 that as an indication that it's done, and only report an
1722 error if ret is -1, in which case wait_msg is the error
1725 primary_msg = wait_msg;
1727 /* We got an error from the sync pipe. If ret is -1, report
1728 both the sync pipe I/O error and the wait error. */
1730 combined_msg = g_strdup_printf("%s\n\n%s", primary_msg, wait_msg);
1731 g_free(primary_msg);
1733 primary_msg = combined_msg;
1737 /* No more child process. */
1738 cap_session->fork_child = -1;
1739 cap_session->fork_child_status = ret;
1742 ws_close(cap_session->signal_pipe_write_fd);
1744 capture_input_closed(cap_session, primary_msg);
1745 g_free(primary_msg);
1749 /* we got a valid message block from the child, process it */
1752 if(!capture_input_new_file(cap_session, buffer)) {
1753 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_input_cb: file failed, closing capture");
1755 /* We weren't able to open the new capture file; user has been
1756 alerted. Close the sync pipe. */
1759 /* The child has sent us a filename which we couldn't open.
1761 This could mean that the child is creating and deleting files
1762 (ring buffer mode) faster than we can handle it.
1764 That should only be the case for very fast file switches;
1765 We can't do much more than telling the child to stop.
1766 (This is the "emergency brake" if the user e.g. wants to
1767 switch files every second).
1769 This can also happen if the user specified "-", meaning
1770 "standard output", as the capture file. */
1771 sync_pipe_stop(cap_session);
1772 capture_input_closed(cap_session, NULL);
1776 case SP_PACKET_COUNT:
1777 npackets = atoi(buffer);
1778 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_input_cb: new packets %u", npackets);
1779 capture_input_new_packets(cap_session, npackets);
1782 /* convert primary message */
1783 pipe_convert_header((guchar*)buffer, 4, &indicator, &primary_len);
1784 primary_msg = buffer+4;
1785 /* convert secondary message */
1786 pipe_convert_header((guchar*)primary_msg + primary_len, 4, &indicator, &secondary_len);
1787 secondary_msg = primary_msg + primary_len + 4;
1788 /* message output */
1789 capture_input_error_message(cap_session, primary_msg, secondary_msg);
1790 /* the capture child will close the sync_pipe, nothing to do for now */
1791 /* (an error message doesn't mean we have to stop capturing) */
1793 case SP_BAD_FILTER: {
1797 ch = strtok(buffer, ":");
1799 indx = (int)strtol(ch, NULL, 10);
1800 ch = strtok(NULL, ":");
1802 capture_input_cfilter_error_message(cap_session, indx, ch);
1803 /* the capture child will close the sync_pipe, nothing to do for now */
1807 capture_input_drops(cap_session, (guint32)strtoul(buffer, NULL, 10));
1810 g_assert_not_reached();
1819 * dumpcap is exiting; wait for it to exit. On success, *msgp is
1820 * unchanged, and the exit status of dumpcap is returned. On
1821 * failure (which includes "dumpcap exited due to being killed by
1822 * a signal or an exception"), *msgp points to an error message
1823 * for the failure, and -1 is returned. In the latter case, *msgp
1824 * must be freed with g_free().
1827 sync_pipe_wait_for_child(int fork_child, gchar **msgp)
1829 int fork_child_status;
1831 GTimeVal start_time;
1836 * GLIB_CHECK_VERSION(2,28,0) adds g_get_real_time which could minimize or
1839 g_get_current_time(&start_time);
1841 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_wait_for_child: wait till child closed");
1842 g_assert(fork_child != -1);
1844 *msgp = NULL; /* assume no error */
1846 if (_cwait(&fork_child_status, fork_child, _WAIT_CHILD) == -1) {
1847 *msgp = g_strdup_printf("Error from cwait(): %s", g_strerror(errno));
1851 * The child exited; return its exit status. Do not treat this as
1854 ret = fork_child_status;
1855 if ((fork_child_status & 0xC0000000) == ERROR_SEVERITY_ERROR) {
1856 /* Probably an exception code */
1857 *msgp = g_strdup_printf("Child dumpcap process died: %s",
1858 win32strexception(fork_child_status));
1863 if (waitpid(fork_child, &fork_child_status, 0) != -1) {
1864 if (WIFEXITED(fork_child_status)) {
1866 * The child exited; return its exit status. Do not treat this as
1869 ret = WEXITSTATUS(fork_child_status);
1870 } else if (WIFSTOPPED(fork_child_status)) {
1871 /* It stopped, rather than exiting. "Should not happen." */
1872 *msgp = g_strdup_printf("Child dumpcap process stopped: %s",
1873 sync_pipe_signame(WSTOPSIG(fork_child_status)));
1875 } else if (WIFSIGNALED(fork_child_status)) {
1876 /* It died with a signal. */
1877 *msgp = g_strdup_printf("Child dumpcap process died: %s%s",
1878 sync_pipe_signame(WTERMSIG(fork_child_status)),
1879 WCOREDUMP(fork_child_status) ? " - core dumped" : "");
1882 /* What? It had to either have exited, or stopped, or died with
1883 a signal; what happened here? */
1884 *msgp = g_strdup_printf("Bad status from waitpid(): %#o",
1888 } else if (errno != ECHILD) {
1889 *msgp = g_strdup_printf("Error from waitpid(): %s", g_strerror(errno));
1892 /* errno == ECHILD ; echld might have already reaped the child */
1893 ret = fetch_dumpcap_pid ? 0 : -1;
1897 g_get_current_time(&end_time);
1898 elapsed = (float) ((end_time.tv_sec - start_time.tv_sec) +
1899 ((end_time.tv_usec - start_time.tv_usec) / 1e6));
1900 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "sync_pipe_wait_for_child: capture child closed after %.3fs", elapsed);
1906 /* convert signal to corresponding name */
1908 sync_pipe_signame(int sig)
1911 static char sigmsg_buf[6+1+3+1];
1920 sigmsg = "Interrupted";
1928 sigmsg = "Illegal instruction";
1932 sigmsg = "Trace trap";
1940 sigmsg = "Arithmetic exception";
1948 sigmsg = "Bus error";
1952 sigmsg = "Segmentation violation";
1955 /* http://metalab.unc.edu/pub/Linux/docs/HOWTO/GCC-HOWTO
1956 Linux is POSIX compliant. These are not POSIX-defined signals ---
1957 ISO/IEC 9945-1:1990 (IEEE Std 1003.1-1990), paragraph B.3.3.1.1 sez:
1959 ``The signals SIGBUS, SIGEMT, SIGIOT, SIGTRAP, and SIGSYS
1960 were omitted from POSIX.1 because their behavior is
1961 implementation dependent and could not be adequately catego-
1962 rized. Conforming implementations may deliver these sig-
1963 nals, but must document the circumstances under which they
1964 are delivered and note any restrictions concerning their
1967 So we only check for SIGSYS on those systems that happen to
1968 implement them (a system can be POSIX-compliant and implement
1969 them, it's just that POSIX doesn't *require* a POSIX-compliant
1970 system to implement them).
1975 sigmsg = "Bad system call";
1980 sigmsg = "Broken pipe";
1984 sigmsg = "Alarm clock";
1988 sigmsg = "Terminated";
1992 /* Returning a static buffer is ok in the context we use it here */
1993 g_snprintf(sigmsg_buf, sizeof sigmsg_buf, "Signal %d", sig);
1994 sigmsg = sigmsg_buf;
2004 static void create_dummy_signal_pipe() {
2005 gchar *dummy_signal_pipe_name;
2007 if (dummy_signal_pipe != NULL) return;
2009 if (!dummy_control_id) {
2010 dummy_control_id = g_strdup_printf("%d.dummy", GetCurrentProcessId());
2013 /* Create the signal pipe */
2014 dummy_signal_pipe_name = g_strdup_printf(SIGNAL_PIPE_FORMAT, dummy_control_id);
2015 dummy_signal_pipe = CreateNamedPipe(utf_8to16(dummy_signal_pipe_name),
2016 PIPE_ACCESS_OUTBOUND, PIPE_TYPE_BYTE, 1, 65535, 65535, 0, NULL);
2017 g_free(dummy_signal_pipe_name);
2020 /* tell the child through the signal pipe that we want to quit the capture */
2022 signal_pipe_capquit_to_child(capture_session *cap_session)
2024 const char quit_msg[] = "QUIT";
2027 g_log(LOG_DOMAIN_CAPTURE, G_LOG_LEVEL_DEBUG, "signal_pipe_capquit_to_child");
2029 /* it doesn't matter *what* we send here, the first byte will stop the capture */
2030 /* simply sending a "QUIT" string */
2031 /*pipe_write_block(cap_session->signal_pipe_write_fd, SP_QUIT, quit_msg);*/
2032 ret = write(cap_session->signal_pipe_write_fd, quit_msg, sizeof quit_msg);
2034 g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
2035 "signal_pipe_capquit_to_child: %d header: error %s", cap_session->signal_pipe_write_fd, g_strerror(errno));
2041 /* user wants to stop the capture run */
2043 sync_pipe_stop(capture_session *cap_session)
2048 gboolean terminate = TRUE;
2051 if (cap_session->fork_child != -1) {
2053 /* send the SIGINT signal to close the capture child gracefully. */
2054 int sts = kill(cap_session->fork_child, SIGINT);
2056 g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
2057 "Sending SIGINT to child failed: %s\n", g_strerror(errno));
2060 #define STOP_SLEEP_TIME 500 /* ms */
2061 #define STOP_CHECK_TIME 50
2062 /* First, use the special signal pipe to try to close the capture child
2065 signal_pipe_capquit_to_child(cap_session);
2067 /* Next, wait for the process to exit on its own */
2068 for (count = 0; count < STOP_SLEEP_TIME / STOP_CHECK_TIME; count++) {
2069 if (GetExitCodeProcess((HANDLE) cap_session->fork_child, &childstatus) &&
2070 childstatus != STILL_ACTIVE) {
2074 Sleep(STOP_CHECK_TIME);
2077 /* Force the issue. */
2079 g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
2080 "sync_pipe_stop: forcing child to exit");
2081 sync_pipe_kill(cap_session->fork_child);
2088 /* Wireshark has to exit, force the capture child to close */
2090 sync_pipe_kill(int fork_child)
2092 if (fork_child != -1) {
2094 int sts = kill(fork_child, SIGTERM); /* SIGTERM so it can clean up if necessary */
2096 g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_WARNING,
2097 "Sending SIGTERM to child failed: %s\n", g_strerror(errno));
2100 /* Remark: This is not the preferred method of closing a process!
2101 * the clean way would be getting the process id of the child process,
2102 * then getting window handle hWnd of that process (using EnumChildWindows),
2103 * and then do a SendMessage(hWnd, WM_CLOSE, 0, 0)
2105 * Unfortunately, I don't know how to get the process id from the
2106 * handle. OpenProcess will get an handle (not a window handle)
2107 * from the process ID; it will not get a window handle from the
2108 * process ID. (How could it? A process can have more than one
2109 * window. For that matter, a process might have *no* windows,
2110 * as a process running dumpcap, the normal child process program,
2113 * Hint: GenerateConsoleCtrlEvent() will only work if both processes are
2114 * running in the same console; that's not necessarily the case for
2115 * us, as we might not be running in a console.
2116 * And this also will require to have the process id.
2118 TerminateProcess((HANDLE) (fork_child), 0);
2123 void capture_sync_set_fetch_dumpcap_pid_cb(void(*cb)(int pid)) {
2124 fetch_dumpcap_pid = cb;
2127 #endif /* HAVE_LIBPCAP */