Qt: Add the "new packet" window^Wdialog^Wwindow.
[metze/wireshark/wip.git] / wireshark-qt.cpp
1 /* wireshark-qt.cpp
2  *
3  * Wireshark - Network traffic analyzer
4  * By Gerald Combs <gerald@wireshark.org>
5  * Copyright 1998 Gerald Combs
6  *
7  * This program is free software; you can redistribute it and/or
8  * modify it under the terms of the GNU General Public License
9  * as published by the Free Software Foundation; either version 2
10  * of the License, or (at your option) any later version.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20  */
21
22 #include <config.h>
23
24 #include <glib.h>
25
26 #ifdef Q_OS_UNIX
27 #include <signal.h>
28 #endif
29
30 #ifdef HAVE_LIBZ
31 #include <zlib.h>       /* to get the libz version number */
32 #endif
33
34 #ifdef HAVE_GETOPT_H
35 #include <getopt.h>
36 #endif
37
38 #ifndef HAVE_GETOPT_LONG
39 #include "wsutil/wsgetopt.h"
40 #endif
41
42 #include <wsutil/clopts_common.h>
43 #include <wsutil/cmdarg_err.h>
44 #include <wsutil/crash_info.h>
45 #include <wsutil/filesystem.h>
46 #include <wsutil/privileges.h>
47 #ifdef HAVE_PLUGINS
48 #include <wsutil/plugins.h>
49 #endif
50 #include <wsutil/report_err.h>
51 #include <wsutil/u3.h>
52 #include <wsutil/ws_version_info.h>
53
54 #include <epan/addr_resolv.h>
55 #include <epan/ex-opt.h>
56 #include <epan/tap.h>
57 #include <epan/stat_tap_ui.h>
58 #include <epan/column.h>
59 #include <epan/disabled_protos.h>
60
61 #ifdef HAVE_KERBEROS
62 #include <epan/packet.h>
63 #include <epan/asn1.h>
64 #include <epan/dissectors/packet-kerberos.h>
65 #endif
66
67 #ifdef HAVE_PLUGINS
68 #include <codecs/codecs.h>
69 #endif
70
71 /* general (not Qt specific) */
72 #include "file.h"
73 #include "color.h"
74 #include "color_filters.h"
75 #include "ui/util.h"
76 #include "log.h"
77
78 #include "ui/alert_box.h"
79 #include "ui/console.h"
80 #include "ui/iface_lists.h"
81 #include "ui/language.h"
82 #include "ui/persfilepath_opt.h"
83 #include "ui/recent.h"
84 #include "ui/simple_dialog.h"
85
86 #include "ui/qt/simple_dialog.h"
87 #include "ui/qt/main_window.h"
88 #include "ui/qt/splash_overlay.h"
89 #include "ui/qt/wireshark_application.h"
90
91 #include "caputils/capture-pcap-util.h"
92
93 #ifdef _WIN32
94 #  include "caputils/capture-wpcap.h"
95 #  include "caputils/capture_wpcap_packet.h"
96 #  include <tchar.h> /* Needed for Unicode */
97 #  include <wsutil/file_util.h>
98 #  include <wsutil/os_version_info.h>
99 #endif /* _WIN32 */
100
101 #ifdef HAVE_AIRPCAP
102 #  include <caputils/airpcap.h>
103 #  include <caputils/airpcap_loader.h>
104 //#  include "airpcap_dlg.h"
105 //#  include "airpcap_gui_utils.h"
106 #endif
107
108 #include "epan/crypt/airpdcap_ws.h"
109
110 #if (QT_VERSION < QT_VERSION_CHECK(5, 0, 0))
111 #include <QTextCodec>
112 #endif
113
114 #include "ui/qt/conversation_dialog.h"
115 #include "ui/qt/endpoint_dialog.h"
116
117 #ifdef HAVE_LIBPCAP
118 capture_options global_capture_opts;
119 #endif
120
121 #ifdef HAVE_AIRPCAP
122 int    airpcap_dll_ret_val = -1;
123 #endif
124
125 GString *comp_info_str, *runtime_info_str;
126
127 /* update the main window */
128 void main_window_update(void)
129 {
130     WiresharkApplication::processEvents();
131 }
132
133 #ifdef HAVE_LIBPCAP
134
135 /* quit a nested main window */
136 void main_window_nested_quit(void)
137 {
138 //    if (gtk_main_level() > 0)
139     wsApp->quit();
140 }
141
142 /* quit the main window */
143 void main_window_quit(void)
144 {
145     wsApp->quit();
146 }
147
148 #endif /* HAVE_LIBPCAP */
149
150
151 // xxx copied from ../gtk/main.c
152 static void
153 print_usage(gboolean for_help_option) {
154     FILE *output;
155
156 #ifdef _WIN32
157     create_console();
158 #endif
159
160     if (for_help_option) {
161         output = stdout;
162         fprintf(output, "Wireshark %s\n"
163                 "Interactively dump and analyze network traffic.\n"
164                 "See http://www.wireshark.org for more information.\n",
165                 get_ws_vcs_version_info());
166     } else {
167         output = stderr;
168     }
169     fprintf(output, "\n");
170     fprintf(output, "Usage: wireshark [options] ... [ <infile> ]\n");
171     fprintf(output, "\n");
172
173 #ifdef HAVE_LIBPCAP
174     fprintf(output, "Capture interface:\n");
175     fprintf(output, "  -i <interface>           name or idx of interface (def: first non-loopback)\n");
176     fprintf(output, "  -f <capture filter>      packet filter in libpcap filter syntax\n");
177     fprintf(output, "  -s <snaplen>             packet snapshot length (def: 65535)\n");
178     fprintf(output, "  -p                       don't capture in promiscuous mode\n");
179     fprintf(output, "  -k                       start capturing immediately (def: do nothing)\n");
180     fprintf(output, "  -S                       update packet display when new packets are captured\n");
181     fprintf(output, "  -l                       turn on automatic scrolling while -S is in use\n");
182 #ifdef HAVE_PCAP_CREATE
183     fprintf(output, "  -I                       capture in monitor mode, if available\n");
184 #endif
185 #if defined(_WIN32) || defined(HAVE_PCAP_CREATE)
186     fprintf(output, "  -B <buffer size>         size of kernel buffer (def: %dMB)\n", DEFAULT_CAPTURE_BUFFER_SIZE);
187 #endif
188     fprintf(output, "  -y <link type>           link layer type (def: first appropriate)\n");
189     fprintf(output, "  -D                       print list of interfaces and exit\n");
190     fprintf(output, "  -L                       print list of link-layer types of iface and exit\n");
191     fprintf(output, "\n");
192     fprintf(output, "Capture stop conditions:\n");
193     fprintf(output, "  -c <packet count>        stop after n packets (def: infinite)\n");
194     fprintf(output, "  -a <autostop cond.> ...  duration:NUM - stop after NUM seconds\n");
195     fprintf(output, "                           filesize:NUM - stop this file after NUM KB\n");
196     fprintf(output, "                              files:NUM - stop after NUM files\n");
197     /*fprintf(output, "\n");*/
198     fprintf(output, "Capture output:\n");
199     fprintf(output, "  -b <ringbuffer opt.> ... duration:NUM - switch to next file after NUM secs\n");
200     fprintf(output, "                           filesize:NUM - switch to next file after NUM KB\n");
201     fprintf(output, "                              files:NUM - ringbuffer: replace after NUM files\n");
202 #endif  /* HAVE_LIBPCAP */
203 #ifdef HAVE_PCAP_REMOTE
204     fprintf(output, "RPCAP options:\n");
205     fprintf(output, "  -A <user>:<password>     use RPCAP password authentication\n");
206 #endif
207     /*fprintf(output, "\n");*/
208     fprintf(output, "Input file:\n");
209     fprintf(output, "  -r <infile>              set the filename to read from (no pipes or stdin!)\n");
210
211     fprintf(output, "\n");
212     fprintf(output, "Processing:\n");
213     fprintf(output, "  -R <read filter>         packet filter in Wireshark display filter syntax\n");
214     fprintf(output, "  -n                       disable all name resolutions (def: all enabled)\n");
215     fprintf(output, "  -N <name resolve flags>  enable specific name resolution(s): \"mntC\"\n");
216
217     fprintf(output, "\n");
218     fprintf(output, "User interface:\n");
219     fprintf(output, "  -C <config profile>      start with specified configuration profile\n");
220     fprintf(output, "  -Y <display filter>      start with the given display filter\n");
221     fprintf(output, "  -g <packet number>       go to specified packet number after \"-r\"\n");
222     fprintf(output, "  -J <jump filter>         jump to the first packet matching the (display)\n");
223     fprintf(output, "                           filter\n");
224     fprintf(output, "  -j                       search backwards for a matching packet after \"-J\"\n");
225     fprintf(output, "  -m <font>                set the font name used for most text\n");
226     fprintf(output, "  -t a|ad|d|dd|e|r|u|ud    output format of time stamps (def: r: rel. to first)\n");
227     fprintf(output, "  -u s|hms                 output format of seconds (def: s: seconds)\n");
228     fprintf(output, "  -X <key>:<value>         eXtension options, see man page for details\n");
229     fprintf(output, "  -z <statistics>          show various statistics, see man page for details\n");
230
231     fprintf(output, "\n");
232     fprintf(output, "Output:\n");
233     fprintf(output, "  -w <outfile|->           set the output filename (or '-' for stdout)\n");
234
235     fprintf(output, "\n");
236     fprintf(output, "Miscellaneous:\n");
237     fprintf(output, "  -h                       display this help and exit\n");
238     fprintf(output, "  -v                       display version info and exit\n");
239     fprintf(output, "  -P <key>:<path>          persconf:path - personal configuration files\n");
240     fprintf(output, "                           persdata:path - personal data files\n");
241     fprintf(output, "  -o <name>:<value> ...    override preference or recent setting\n");
242     fprintf(output, "  -K <keytab>              keytab file to use for kerberos decryption\n");
243 #ifndef _WIN32
244     fprintf(output, "  --display=DISPLAY        X display to use\n");
245 #endif
246     fprintf(output, "\nNOTE: Not all options are implemented in the Qt port.\n");
247
248 #ifdef _WIN32
249     destroy_console();
250 #endif
251 }
252
253 /*
254  * Report an error in command-line arguments.
255  * Creates a console on Windows.
256  */
257 // xxx copied from ../gtk/main.c
258 static void
259 wireshark_cmdarg_err(const char *fmt, va_list ap)
260 {
261 #ifdef _WIN32
262     create_console();
263 #endif
264     fprintf(stderr, "wireshark: ");
265     vfprintf(stderr, fmt, ap);
266     fprintf(stderr, "\n");
267 }
268
269 /*
270  * Report additional information for an error in command-line arguments.
271  * Creates a console on Windows.
272  * XXX - pop this up in a window of some sort on UNIX+X11 if the controlling
273  * terminal isn't the standard error?
274  */
275 // xxx copied from ../gtk/main.c
276 static void
277 wireshark_cmdarg_err_cont(const char *fmt, va_list ap)
278 {
279 #ifdef _WIN32
280     create_console();
281 #endif
282     vfprintf(stderr, fmt, ap);
283     fprintf(stderr, "\n");
284 }
285
286 // xxx based from ../gtk/main.c:get_gtk_compiled_info
287 static void
288 get_wireshark_qt_compiled_info(GString *str)
289 {
290     g_string_append(str, "with ");
291     g_string_append_printf(str,
292 #ifdef QT_VERSION
293                     "Qt %s", QT_VERSION_STR);
294 #else
295                     "Qt (version unknown)");
296 #endif
297
298     /* Capture libraries */
299     g_string_append(str, ", ");
300     get_compiled_caplibs_version(str);
301
302     /* LIBZ */
303     g_string_append(str, ", ");
304 #ifdef HAVE_LIBZ
305     g_string_append(str, "with libz ");
306 #ifdef ZLIB_VERSION
307     g_string_append(str, ZLIB_VERSION);
308 #else /* ZLIB_VERSION */
309     g_string_append(str, "(version unknown)");
310 #endif /* ZLIB_VERSION */
311 #else /* HAVE_LIBZ */
312     g_string_append(str, "without libz");
313 #endif /* HAVE_LIBZ */
314 }
315
316 // xxx copied from ../gtk/main.c
317 static void
318 get_gui_compiled_info(GString *str)
319 {
320     epan_get_compiled_version_info(str);
321
322     g_string_append(str, ", ");
323     g_string_append(str, "without PortAudio");
324
325     g_string_append(str, ", ");
326 #ifdef HAVE_AIRPCAP
327     get_compiled_airpcap_version(str);
328 #else
329     g_string_append(str, "without AirPcap");
330 #endif
331 }
332
333 // xxx copied from ../gtk/main.c
334 static void
335 get_wireshark_runtime_info(GString *str)
336 {
337 #ifdef HAVE_LIBPCAP
338     /* Capture libraries */
339     g_string_append(str, ", ");
340     get_runtime_caplibs_version(str);
341 #endif
342
343     /* zlib */
344 #if defined(HAVE_LIBZ) && !defined(_WIN32)
345     g_string_append_printf(str, ", with libz %s", zlibVersion());
346 #endif
347
348     /* stuff used by libwireshark */
349     epan_get_runtime_version_info(str);
350
351 #ifdef HAVE_AIRPCAP
352     g_string_append(str, ", ");
353     get_runtime_airpcap_version(str);
354 #endif
355
356     if(u3_active()) {
357         g_string_append(str, ", ");
358         u3_runtime_info(str);
359     }
360 }
361
362 #ifdef HAVE_LIBPCAP
363 /*  Check if there's something important to tell the user during startup.
364  *  We want to do this *after* showing the main window so that any windows
365  *  we pop up will be above the main window.
366  */
367 static void
368 check_and_warn_user_startup(const QString &cf_name)
369 {
370 #ifndef _WIN32
371     Q_UNUSED(cf_name)
372 #endif
373     gchar               *cur_user, *cur_group;
374
375     /* Tell the user not to run as root. */
376     if (running_with_special_privs() && recent.privs_warn_if_elevated) {
377         cur_user = get_cur_username();
378         cur_group = get_cur_groupname();
379         simple_message_box(ESD_TYPE_WARN, &recent.privs_warn_if_elevated,
380         "Running as user \"%s\" and group \"%s\".\n"
381         "This could be dangerous.\n\n"
382         "If you're running Wireshark this way in order to perform live capture, "
383         "you may want to be aware that there is a better way documented at\n"
384         "http://wiki.wireshark.org/CaptureSetup/CapturePrivileges", cur_user, cur_group);
385         g_free(cur_user);
386         g_free(cur_group);
387     }
388
389 #ifdef _WIN32
390     /* Warn the user if npf.sys isn't loaded. */
391     if (!get_stdin_capture() && cf_name.isEmpty() && !npf_sys_is_running() && recent.privs_warn_if_no_npf && get_windows_major_version() >= 6) {
392         simple_message_box(ESD_TYPE_WARN, &recent.privs_warn_if_no_npf, "%s",
393         "The NPF driver isn't running. You may have trouble\n"
394         "capturing or listing interfaces.");
395     }
396 #endif
397
398 }
399 #endif
400
401 #ifdef _WIN32
402 // Try to avoid library search path collisions. QCoreApplication will
403 // search QT_INSTALL_PREFIX/plugins for platform DLLs before searching
404 // the application directory. If
405 //
406 // - You have Qt version 5.x.y installed in the default location
407 //   (C:\Qt\5.x) on your machine.
408 //
409 // and
410 //
411 // - You install Wireshark that was built on a machine with Qt version
412 //   5.x.z installed in the default location.
413 //
414 // Qt5Core.dll will load qwindows.dll from your local C:\Qt\5.x\...\plugins
415 // directory. This may not be compatible with qwindows.dll from that
416 // same path on the build machine. At any rate, loading DLLs from paths
417 // you don't control is ill-advised. We work around this by removing every
418 // path except our application directory.
419
420 static inline void
421 reset_library_path(void)
422 {
423     QString app_path = QDir(get_progfile_dir()).path();
424     foreach (QString path, QCoreApplication::libraryPaths()) {
425         QCoreApplication::removeLibraryPath(path);
426     }
427     QCoreApplication::addLibraryPath(app_path);
428 }
429 #endif
430
431 /* And now our feature presentation... [ fade to music ] */
432 int main(int argc, char *argv[])
433 {
434     MainWindow *main_w;
435
436     int                  opt;
437     gboolean             arg_error = FALSE;
438
439 #ifdef _WIN32
440     WSADATA            wsaData;
441 #endif  /* _WIN32 */
442
443     char                *rf_path;
444     int                  rf_open_errno;
445     char                *gdp_path, *dp_path;
446 #ifdef HAVE_LIBPCAP
447     int                  err;
448     gboolean             start_capture = FALSE;
449     gboolean             list_link_layer_types = FALSE;
450     GList               *if_list;
451     gchar               *err_str;
452     int                  status;
453 #else
454     gboolean             capture_option_specified = FALSE;
455 #ifdef _WIN32
456 #ifdef HAVE_AIRPCAP
457     gchar               *err_str;
458 #endif
459 #endif
460 #endif
461     e_prefs             *prefs_p;
462     char                 badopt;
463     guint                go_to_packet = 0;
464
465     QString              dfilter, read_filter;
466
467     cmdarg_err_init(wireshark_cmdarg_err, wireshark_cmdarg_err_cont);
468
469 #ifdef _WIN32
470     create_app_running_mutex();
471 #endif
472
473     /*
474      * Get credential information for later use, and drop privileges
475      * before doing anything else.
476      * Let the user know if anything happened.
477      */
478     init_process_policies();
479     relinquish_special_privs_perm();
480
481     /*
482      * Attempt to get the pathname of the executable file.
483      */
484     /* init_progfile_dir_error = */ init_progfile_dir(argv[0], main);
485     g_log(NULL, G_LOG_LEVEL_DEBUG, "progfile_dir: %s", get_progfile_dir());
486
487     /* Get the compile-time version information string */
488     // XXX qtshark
489     comp_info_str = get_compiled_version_info(get_wireshark_qt_compiled_info,
490                                               get_gui_compiled_info);
491
492     /* Assemble the run-time version information string */
493     // xxx qtshark
494     runtime_info_str = get_runtime_version_info(get_wireshark_runtime_info);
495
496     /*
497      * In order to have the -X opts assigned before the wslua machine starts
498      * we need to call getopt_long before epan_init() gets called.
499      *
500      * In addition, we process "console only" parameters (ones where we
501      * send output to the console and exit) here, so we don't start Qt
502      * if we're only showing command-line help or version information.
503      *
504      * XXX - this pre-scan is done before we start Qt, so we haven't
505      * run WiresharkApplication's constructor on the arguments.  That
506      * means that Qt arguments have not been removed from the argument
507      * list; those arguments begin with "-", and may be treated as
508      * errors by getopt_long().
509      *
510      * We thus ignore errors - *and* set "opterr" to 0 to suppress the
511      * error messages.
512      *
513      * XXX - is there some way to parse and remove Qt arguments without
514      * starting up the GUI, which we can call before calling this?
515      *
516      * In order to handle, for example, -o options, we also need to call it
517      * *after* epan_init() gets called, so that the dissectors have had a
518      * chance to register their preferences, so we have another getopt_long()
519      * call later.
520      *
521      * XXX - can we do this all with one getopt_long() call, saving the
522      * arguments we can't handle until after initializing libwireshark,
523      * and then process them after initializing libwireshark?
524      *
525      * Note that we don't want to initialize libwireshark until after the
526      * GUI is up, as that can take a while, and we want a window of some
527      * sort up to show progress while that's happening.
528      */
529     // XXX Should the remaining code be in WiresharkApplcation::WiresharkApplication?
530 #define OPTSTRING OPTSTRING_CAPTURE_COMMON "C:g:Hh" "jJ:kK:lm:nN:o:P:r:R:St:u:vw:X:Y:z:"
531     static const struct option long_options[] = {
532         {(char *)"help", no_argument, NULL, 'h'},
533         {(char *)"read-file", required_argument, NULL, 'r' },
534         {(char *)"read-filter", required_argument, NULL, 'R' },
535         {(char *)"display-filter", required_argument, NULL, 'Y' },
536         {(char *)"version", no_argument, NULL, 'v'},
537         LONGOPT_CAPTURE_COMMON
538         {0, 0, 0, 0 }
539     };
540     static const char optstring[] = OPTSTRING;
541
542     opterr = 0;
543
544     while ((opt = getopt_long(argc, argv, optstring, long_options, NULL)) != -1) {
545         switch (opt) {
546             case 'C':        /* Configuration Profile */
547                 if (profile_exists (optarg, FALSE)) {
548                     set_profile_name (optarg);
549                 } else {
550                     cmdarg_err("Configuration Profile \"%s\" does not exist", optarg);
551                     exit(1);
552                 }
553                 break;
554             case 'D':        /* Print a list of capture devices and exit */
555 #ifdef HAVE_LIBPCAP
556                 if_list = capture_interface_list(&err, &err_str, NULL);
557                 if (if_list == NULL) {
558                     if (err == 0)
559                         cmdarg_err("There are no interfaces on which a capture can be done");
560                     else {
561                         cmdarg_err("%s", err_str);
562                         g_free(err_str);
563                     }
564                     exit(2);
565                 }
566 #ifdef _WIN32
567                 create_console();
568 #endif /* _WIN32 */
569                 capture_opts_print_interfaces(if_list);
570                 free_interface_list(if_list);
571 #ifdef _WIN32
572                 destroy_console();
573 #endif /* _WIN32 */
574                 exit(0);
575 #else /* HAVE_LIBPCAP */
576                 capture_option_specified = TRUE;
577                 arg_error = TRUE;
578 #endif /* HAVE_LIBPCAP */
579                 break;
580             case 'h':        /* Print help and exit */
581                 print_usage(TRUE);
582                 exit(0);
583                 break;
584 #ifdef _WIN32
585             case 'i':
586                 if (strcmp(optarg, "-") == 0)
587                     set_stdin_capture(TRUE);
588                 break;
589 #endif
590             case 'P':        /* Personal file directory path settings - change these before the Preferences and alike are processed */
591                 if (!persfilepath_opt(opt, optarg)) {
592                     cmdarg_err("-P flag \"%s\" failed (hint: is it quoted and existing?)", optarg);
593                     exit(2);
594                 }
595                 break;
596             case 'v':        /* Show version and exit */
597 #ifdef _WIN32
598                 create_console();
599 #endif
600                 show_version("Wireshark", comp_info_str, runtime_info_str);
601 #ifdef _WIN32
602                 destroy_console();
603 #endif
604                 exit(0);
605                 break;
606             case 'X':
607                 /*
608                  *  Extension command line options have to be processed before
609                  *  we call epan_init() as they are supposed to be used by dissectors
610                  *  or taps very early in the registration process.
611                  */
612                 ex_opt_add(optarg);
613                 break;
614             case '?':        /* Ignore errors - the "real" scan will catch them. */
615                 break;
616         }
617     }
618
619 #ifdef _WIN32
620     reset_library_path();
621 #endif
622
623     /* Create The Wireshark app */
624     WiresharkApplication ws_app(argc, argv);
625
626     /* initialize the funnel mini-api */
627     // xxx qtshark
628     //initialize_funnel_ops();
629
630     AirPDcapInitContext(&airpdcap_ctx);
631
632 // xxx qtshark
633 #ifdef _WIN32
634     /* Load wpcap if possible. Do this before collecting the run-time version information */
635     load_wpcap();
636
637     /* ... and also load the packet.dll from wpcap */
638     wpcap_packet_load();
639
640 #ifdef HAVE_AIRPCAP
641     /* Load the airpcap.dll.  This must also be done before collecting
642      * run-time version information. */
643     airpcap_dll_ret_val = load_airpcap();
644
645     switch (airpcap_dll_ret_val) {
646     case AIRPCAP_DLL_OK:
647         /* load the airpcap interfaces */
648         airpcap_if_list = get_airpcap_interface_list(&err, &err_str);
649
650         if (airpcap_if_list == NULL || g_list_length(airpcap_if_list) == 0){
651             if (err == CANT_GET_AIRPCAP_INTERFACE_LIST && err_str != NULL) {
652                 simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "%s", "Failed to open Airpcap Adapters.");
653                 g_free(err_str);
654             }
655             airpcap_if_active = NULL;
656
657         } else {
658
659             /* select the first ad default (THIS SHOULD BE CHANGED) */
660             airpcap_if_active = airpcap_get_default_if(airpcap_if_list);
661         }
662         break;
663 #if 0
664     /*
665      * XXX - Maybe we need to warn the user if one of the following happens???
666      */
667     case AIRPCAP_DLL_OLD:
668         simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "%s","AIRPCAP_DLL_OLD\n");
669         break;
670
671     case AIRPCAP_DLL_ERROR:
672         simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "%s","AIRPCAP_DLL_ERROR\n");
673         break;
674
675     case AIRPCAP_DLL_NOT_FOUND:
676         simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK, "%s","AIRPCAP_DDL_NOT_FOUND\n");
677         break;
678 #endif
679     }
680 #endif /* HAVE_AIRPCAP */
681 #endif /* _WIN32 */
682
683     QString locale;
684     QString cf_name;
685     unsigned int in_file_type = WTAP_TYPE_AUTO;
686
687     // In Qt 5, C strings are treated always as UTF-8 when converted to
688     // QStrings; in Qt 4, the codec must be set to make that happen
689 #if (QT_VERSION < QT_VERSION_CHECK(5, 0, 0))
690     // Hopefully we won't have to use QString::fromUtf8() in as many places.
691     QTextCodec *utf8codec = QTextCodec::codecForName("UTF-8");
692     QTextCodec::setCodecForCStrings(utf8codec);
693     // XXX - QObject doesn't *have* a tr method in 5.0, as far as I can see...
694     QTextCodec::setCodecForTr(utf8codec);
695 #endif
696
697     /* Add it to the information to be reported on a crash. */
698     ws_add_crash_info("Wireshark %s\n"
699            "\n"
700            "%s"
701            "\n"
702            "%s",
703         get_ws_vcs_version_info(), comp_info_str->str, runtime_info_str->str);
704
705 #ifdef _WIN32
706     /* Start windows sockets */
707     WSAStartup( MAKEWORD( 1, 1 ), &wsaData );
708 #endif  /* _WIN32 */
709
710     profile_store_persconffiles(TRUE);
711
712     /* Read the profile independent recent file.  We have to do this here so we can */
713     /* set the profile before it can be set from the command line parameter */
714     recent_read_static(&rf_path, &rf_open_errno);
715     if (rf_path != NULL && rf_open_errno != 0) {
716         simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK,
717                       "Could not open common recent file\n\"%s\": %s.",
718                       rf_path, strerror(rf_open_errno));
719     }
720     wsApp->emitAppSignal(WiresharkApplication::StaticRecentFilesRead);
721
722     /* Init the "Open file" dialog directory */
723     /* (do this after the path settings are processed) */
724
725     /* Read the profile dependent (static part) of the recent file. */
726     /* Only the static part of it will be read, as we don't have the gui now to fill the */
727     /* recent lists which is done in the dynamic part. */
728     /* We have to do this already here, so command line parameters can overwrite these values. */
729     recent_read_profile_static(&rf_path, &rf_open_errno);
730     if (rf_path != NULL && rf_open_errno != 0) {
731         simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK,
732                       "Could not open recent file\n\"%s\": %s.",
733                       rf_path, g_strerror(rf_open_errno));
734     }
735
736     // Initialize our language
737     read_language_prefs();
738     locale = QString(language);
739     wsApp->loadLanguage(locale);
740
741     g_log(LOG_DOMAIN_MAIN, G_LOG_LEVEL_DEBUG, "Translator %s", locale.toStdString().c_str());
742
743     // Init the main window (and splash)
744     main_w = new(MainWindow);
745     main_w->show();
746     // We may not need a queued connection here but it would seem to make sense
747     // to force the issue.
748     main_w->connect(&ws_app, SIGNAL(openCaptureFile(QString&,QString&,unsigned int)),
749             main_w, SLOT(openCaptureFile(QString&,QString&,unsigned int)));
750
751     /* Init the "Open file" dialog directory */
752     /* (do this after the path settings are processed) */
753
754     /* Read the profile dependent (static part) of the recent file. */
755     /* Only the static part of it will be read, as we don't have the gui now to fill the */
756     /* recent lists which is done in the dynamic part. */
757     /* We have to do this already here, so command line parameters can overwrite these values. */
758     recent_read_profile_static(&rf_path, &rf_open_errno);
759     if (rf_path != NULL && rf_open_errno != 0) {
760       simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK,
761             "Could not open recent file\n\"%s\": %s.",
762             rf_path, g_strerror(rf_open_errno));
763     }
764     wsApp->emitAppSignal(WiresharkApplication::StaticRecentFilesRead);
765
766     if (recent.gui_fileopen_remembered_dir &&
767         test_for_directory(recent.gui_fileopen_remembered_dir) == EISDIR) {
768       wsApp->setLastOpenDir(recent.gui_fileopen_remembered_dir);
769     } else {
770       wsApp->setLastOpenDir(get_persdatafile_dir());
771     }
772
773 #ifdef Q_OS_UNIX
774     // Replicates behavior in gtk_init();
775     signal(SIGPIPE, SIG_IGN);
776 #endif
777
778     set_console_log_handler();
779
780 #ifdef HAVE_LIBPCAP
781     /* Set the initial values in the capture options. This might be overwritten
782        by preference settings and then again by the command line parameters. */
783     capture_opts_init(&global_capture_opts);
784 #endif
785
786     init_report_err(failure_alert_box, open_failure_alert_box,
787                     read_failure_alert_box, write_failure_alert_box);
788
789     init_open_routines();
790
791 #ifdef HAVE_PLUGINS
792     /* Register all the plugin types we have. */
793     epan_register_plugin_types(); /* Types known to libwireshark */
794     wtap_register_plugin_types(); /* Types known to libwiretap */
795     codec_register_plugin_types(); /* Types known to libcodec */
796
797     /* Scan for plugins.  This does *not* call their registration routines;
798        that's done later. */
799     scan_plugins();
800
801     /* Register all libwiretap plugin modules. */
802     register_all_wiretap_modules();
803
804     /* Register all audio codec plugins. */
805     register_all_codecs();
806 #endif
807
808     /* Register all dissectors; we must do this before checking for the
809        "-G" flag, as the "-G" flag dumps information registered by the
810        dissectors, and we must do it before we read the preferences, in
811        case any dissectors register preferences. */
812     epan_init(register_all_protocols,register_all_protocol_handoffs,
813               splash_update, NULL);
814
815     splash_update(RA_LISTENERS, NULL, NULL);
816
817     /* Register all tap listeners; we do this before we parse the arguments,
818        as the "-z" argument can specify a registered tap. */
819
820     /* we register the plugin taps before the other taps because
821             stats_tree taps plugins will be registered as tap listeners
822             by stats_tree_stat.c and need to registered before that */
823
824     g_log(NULL, G_LOG_LEVEL_DEBUG, "plugin_dir: %s", get_plugin_dir());
825 #ifdef HAVE_PLUGINS
826     register_all_plugin_tap_listeners();
827 #endif
828
829     register_all_tap_listeners();
830     conversation_table_set_gui_info(init_conversation_table);
831     hostlist_table_set_gui_info(init_endpoint_table);
832
833     if (ex_opt_count("read_format") > 0) {
834         in_file_type = open_info_name_to_type(ex_opt_get_next("read_format"));
835     }
836
837     splash_update(RA_PREFERENCES, NULL, NULL);
838
839     prefs_p = ws_app.readConfigurationFiles(&gdp_path, &dp_path);
840
841     /*
842      * To reset the options parser, set optreset to 1 on platforms that
843      * have optreset (documented in *BSD and OS X, apparently present but
844      * not documented in Solaris - the Illumos repository seems to
845      * suggest that the first Solaris getopt_long(), at least as of 2004,
846      * was based on the NetBSD one, it had optreset) and set optind to 1,
847      * and set optind to 0 otherwise (documented as working in the GNU
848      * getopt_long().  Setting optind to 0 didn't originally work in the
849      * NetBSD one, but that was added later - we don't want to depend on
850      * it if we have optreset).
851      *
852      * Also reset opterr to 1, so that error messages are printed by
853      * getopt_long().
854      *
855      * XXX - if we want to control all the command-line option errors, so
856      * that we can display them where we choose (e.g., in a window), we'd
857      * want to leave opterr as 0, and produce our own messages using optopt.
858      * We'd have to check the value of optopt to see if it's a valid option
859      * letter, in which case *presumably* the error is "this option requires
860      * an argument but none was specified", or not a valid option letter,
861      * in which case *presumably* the error is "this option isn't valid".
862      * Some versions of getopt() let you supply a option string beginning
863      * with ':', which means that getopt() will return ':' rather than '?'
864      * for "this option requires an argument but none was specified", but
865      * not all do.  But we're now using getopt_long() - what does it do?
866      */
867 #ifdef HAVE_OPTRESET
868     optreset = 1;
869     optind = 1;
870 #else
871     optind = 0;
872 #endif
873     opterr = 1;
874
875     /* Now get our args */
876     while ((opt = getopt_long(argc, argv, optstring, long_options, NULL)) != -1) {
877         switch (opt) {
878         /*** capture option specific ***/
879         case 'a':        /* autostop criteria */
880         case 'b':        /* Ringbuffer option */
881         case 'c':        /* Capture xxx packets */
882         case 'f':        /* capture filter */
883         case 'k':        /* Start capture immediately */
884         case 'H':        /* Hide capture info dialog box */
885         case 'p':        /* Don't capture in promiscuous mode */
886         case 'i':        /* Use interface x */
887 #ifdef HAVE_PCAP_CREATE
888         case 'I':        /* Capture in monitor mode, if available */
889 #endif
890 #ifdef HAVE_PCAP_REMOTE
891         case 'A':        /* Authentication */
892 #endif
893         case 's':        /* Set the snapshot (capture) length */
894         case 'S':        /* "Sync" mode: used for following file ala tail -f */
895         case 'w':        /* Write to capture file xxx */
896         case 'y':        /* Set the pcap data link type */
897 #if defined(_WIN32) || defined(HAVE_PCAP_CREATE)
898         case 'B':        /* Buffer size */
899 #endif /* _WIN32 or HAVE_PCAP_CREATE */
900 #ifdef HAVE_LIBPCAP
901             status = capture_opts_add_opt(&global_capture_opts, opt, optarg,
902                                           &start_capture);
903             if(status != 0) {
904                 exit(status);
905             }
906 #else
907             capture_option_specified = TRUE;
908             arg_error = TRUE;
909 #endif
910             break;
911 #ifdef HAVE_KERBEROS
912         case 'K':        /* Kerberos keytab file */
913             read_keytab_file(optarg);
914             break;
915 #endif
916
917         /*** all non capture option specific ***/
918         case 'C':
919             /* Configuration profile settings were already processed just ignore them this time*/
920             break;
921         case 'j':        /* Search backwards for a matching packet from filter in option J */
922             /* Not supported yet */
923             break;
924         case 'g':        /* Go to packet with the given packet number */
925             go_to_packet = get_positive_int(optarg, "go to packet");
926             break;
927         case 'J':        /* Jump to the first packet which matches the filter criteria */
928             /* Not supported yet */
929             break;
930         case 'l':        /* Automatic scrolling in live capture mode */
931 #ifdef HAVE_LIBPCAP
932             /* Not supported yet */
933 #else
934             capture_option_specified = TRUE;
935             arg_error = TRUE;
936 #endif
937             break;
938         case 'L':        /* Print list of link-layer types and exit */
939 #ifdef HAVE_LIBPCAP
940                 list_link_layer_types = TRUE;
941 #else
942                 capture_option_specified = TRUE;
943                 arg_error = TRUE;
944 #endif
945             break;
946         case 'm':        /* Fixed-width font for the display */
947             /* Not supported yet */
948             break;
949         case 'n':        /* No name resolution */
950             gbl_resolv_flags.mac_name = FALSE;
951             gbl_resolv_flags.network_name = FALSE;
952             gbl_resolv_flags.transport_name = FALSE;
953             gbl_resolv_flags.concurrent_dns = FALSE;
954             break;
955         case 'N':        /* Select what types of addresses/port #s to resolve */
956             badopt = string_to_name_resolve(optarg, &gbl_resolv_flags);
957             if (badopt != '\0') {
958                 cmdarg_err("-N specifies unknown resolving option '%c'; valid options are 'm', 'n', and 't'",
959                            badopt);
960                 exit(1);
961             }
962             break;
963         case 'o':        /* Override preference from command line */
964             switch (prefs_set_pref(optarg)) {
965                 case PREFS_SET_OK:
966                     break;
967                 case PREFS_SET_SYNTAX_ERR:
968                     cmdarg_err("Invalid -o flag \"%s\"", optarg);
969                     exit(1);
970                     break;
971                 case PREFS_SET_NO_SUCH_PREF:
972                 /* not a preference, might be a recent setting */
973                     switch (recent_set_arg(optarg)) {
974                         case PREFS_SET_OK:
975                             break;
976                         case PREFS_SET_SYNTAX_ERR:
977                             /* shouldn't happen, checked already above */
978                             cmdarg_err("Invalid -o flag \"%s\"", optarg);
979                             exit(1);
980                             break;
981                         case PREFS_SET_NO_SUCH_PREF:
982                         case PREFS_SET_OBSOLETE:
983                             cmdarg_err("-o flag \"%s\" specifies unknown preference/recent value",
984                                        optarg);
985                             exit(1);
986                             break;
987                         default:
988                             g_assert_not_reached();
989                     }
990                     break;
991                 case PREFS_SET_OBSOLETE:
992                     cmdarg_err("-o flag \"%s\" specifies obsolete preference",
993                                optarg);
994                     exit(1);
995                     break;
996                 default:
997                     g_assert_not_reached();
998             }
999             break;
1000         case 'P':
1001             /* Path settings were already processed just ignore them this time*/
1002             break;
1003         case 'r':
1004             cf_name = optarg;
1005             break;
1006         case 'R':        /* Read file filter */
1007             read_filter = QString(optarg);
1008             break;
1009         case 't':        /* Time stamp type */
1010             if (strcmp(optarg, "r") == 0)
1011                 timestamp_set_type(TS_RELATIVE);
1012             else if (strcmp(optarg, "a") == 0)
1013                 timestamp_set_type(TS_ABSOLUTE);
1014             else if (strcmp(optarg, "ad") == 0)
1015                 timestamp_set_type(TS_ABSOLUTE_WITH_YMD);
1016             else if (strcmp(optarg, "adoy") == 0)
1017                 timestamp_set_type(TS_ABSOLUTE_WITH_YDOY);
1018             else if (strcmp(optarg, "d") == 0)
1019                 timestamp_set_type(TS_DELTA);
1020             else if (strcmp(optarg, "dd") == 0)
1021                 timestamp_set_type(TS_DELTA_DIS);
1022             else if (strcmp(optarg, "e") == 0)
1023                 timestamp_set_type(TS_EPOCH);
1024             else if (strcmp(optarg, "u") == 0)
1025                 timestamp_set_type(TS_UTC);
1026             else if (strcmp(optarg, "ud") == 0)
1027                 timestamp_set_type(TS_UTC_WITH_YMD);
1028             else if (strcmp(optarg, "udoy") == 0)
1029                 timestamp_set_type(TS_UTC_WITH_YDOY);
1030             else {
1031                 cmdarg_err("Invalid time stamp type \"%s\"", optarg);
1032                 cmdarg_err_cont(
1033 "It must be \"a\" for absolute, \"ad\" for absolute with YYYY-MM-DD date,");
1034                 cmdarg_err_cont(
1035 "\"adoy\" for absolute with YYYY/DOY date, \"d\" for delta,");
1036                 cmdarg_err_cont(
1037 "\"dd\" for delta displayed, \"e\" for epoch, \"r\" for relative,");
1038                 cmdarg_err_cont(
1039 "\"u\" for absolute UTC, \"ud\" for absolute UTC with YYYY-MM-DD date,");
1040                 cmdarg_err_cont(
1041 "or \"udoy\" for absolute UTC with YYYY/DOY date.");
1042                 exit(1);
1043             }
1044             break;
1045         case 'u':        /* Seconds type */
1046             if (strcmp(optarg, "s") == 0)
1047                 timestamp_set_seconds_type(TS_SECONDS_DEFAULT);
1048             else if (strcmp(optarg, "hms") == 0)
1049                 timestamp_set_seconds_type(TS_SECONDS_HOUR_MIN_SEC);
1050             else {
1051                 cmdarg_err("Invalid seconds type \"%s\"", optarg);
1052                 cmdarg_err_cont(
1053 "It must be \"s\" for seconds or \"hms\" for hours, minutes and seconds.");
1054                 exit(1);
1055             }
1056             break;
1057         case 'X':
1058             /* ext ops were already processed just ignore them this time*/
1059             break;
1060         case 'Y':
1061             dfilter = QString(optarg);
1062             break;
1063         case 'z':
1064             /* We won't call the init function for the stat this soon
1065              as it would disallow MATE's fields (which are registered
1066              by the preferences set callback) from being used as
1067              part of a tap filter.  Instead, we just add the argument
1068              to a list of stat arguments. */
1069             if (strcmp("help", optarg) == 0) {
1070               fprintf(stderr, "wireshark: The available statistics for the \"-z\" option are:\n");
1071               list_stat_cmd_args();
1072               exit(0);
1073             }
1074             if (!process_stat_cmd_arg(optarg)) {
1075                 cmdarg_err("Invalid -z argument.");
1076                 cmdarg_err_cont("  -z argument must be one of :");
1077                 list_stat_cmd_args();
1078                 exit(1);
1079             }
1080             break;
1081         default:
1082         case '?':        /* Bad flag - print usage message */
1083             print_usage(FALSE);
1084             exit(0);
1085             break;
1086         }
1087     }
1088
1089     if (!arg_error) {
1090         argc -= optind;
1091         argv += optind;
1092         if (argc >= 1) {
1093             if (!cf_name.isEmpty()) {
1094                 /*
1095                  * Input file name specified with "-r" *and* specified as a regular
1096                  * command-line argument.
1097                  */
1098                 cmdarg_err("File name specified both with -r and regular argument");
1099                 arg_error = TRUE;
1100             } else {
1101                 /*
1102                  * Input file name not specified with "-r", and a command-line argument
1103                  * was specified; treat it as the input file name.
1104                  *
1105                  * Yes, this is different from tshark, where non-flag command-line
1106                  * arguments are a filter, but this works better on GUI desktops
1107                  * where a command can be specified to be run to open a particular
1108                  * file - yes, you could have "-r" as the last part of the command,
1109                  * but that's a bit ugly.
1110                  */
1111                 cf_name = argv[0];
1112
1113             }
1114             argc--;
1115             argv++;
1116         }
1117
1118         if (argc != 0) {
1119             /*
1120              * Extra command line arguments were specified; complain.
1121              */
1122             cmdarg_err("Invalid argument: %s", argv[0]);
1123             arg_error = TRUE;
1124         }
1125     }
1126     if (arg_error) {
1127 #ifndef HAVE_LIBPCAP
1128         if (capture_option_specified) {
1129             cmdarg_err("This version of Wireshark was not built with support for capturing packets.");
1130         }
1131 #endif
1132         print_usage(FALSE);
1133         exit(1);
1134     }
1135
1136     /* Removed thread code:
1137      * https://code.wireshark.org/review/gitweb?p=wireshark.git;a=commit;h=9e277ae6154fd04bf6a0a34ec5655a73e5a736a3
1138      */
1139
1140     // XXX Is there a better place to set the timestamp format & precision?
1141     timestamp_set_type(recent.gui_time_format);
1142     timestamp_set_precision(recent.gui_time_precision);
1143     timestamp_set_seconds_type(TS_SECONDS_DEFAULT);
1144
1145 #ifdef HAVE_LIBPCAP
1146     fill_in_local_interfaces(main_window_update);
1147
1148     if (start_capture && list_link_layer_types) {
1149         /* Specifying *both* is bogus. */
1150         cmdarg_err("You can't specify both -L and a live capture.");
1151         exit(1);
1152     }
1153
1154     if (list_link_layer_types) {
1155         /* We're supposed to list the link-layer types for an interface;
1156            did the user also specify a capture file to be read? */
1157         if (!cf_name.isEmpty()) {
1158             /* Yes - that's bogus. */
1159             cmdarg_err("You can't specify -L and a capture file to be read.");
1160         exit(1);
1161         }
1162         /* No - did they specify a ring buffer option? */
1163         if (global_capture_opts.multi_files_on) {
1164             cmdarg_err("Ring buffer requested, but a capture isn't being done.");
1165             exit(1);
1166         }
1167     } else {
1168         /* We're supposed to do a live capture; did the user also specify
1169            a capture file to be read? */
1170         if (start_capture && !cf_name.isEmpty()) {
1171             /* Yes - that's bogus. */
1172             cmdarg_err("You can't specify both a live capture and a capture file to be read.");
1173             exit(1);
1174         }
1175
1176         /* No - was the ring buffer option specified and, if so, does it make
1177            sense? */
1178         if (global_capture_opts.multi_files_on) {
1179             /* Ring buffer works only under certain conditions:
1180              a) ring buffer does not work with temporary files;
1181              b) real_time_mode and multi_files_on are mutually exclusive -
1182              real_time_mode takes precedence;
1183              c) it makes no sense to enable the ring buffer if the maximum
1184              file size is set to "infinite". */
1185             if (global_capture_opts.save_file == NULL) {
1186                 cmdarg_err("Ring buffer requested, but capture isn't being saved to a permanent file.");
1187                 global_capture_opts.multi_files_on = FALSE;
1188             }
1189             if (!global_capture_opts.has_autostop_filesize && !global_capture_opts.has_file_duration) {
1190                 cmdarg_err("Ring buffer requested, but no maximum capture file size or duration were specified.");
1191                 /* XXX - this must be redesigned as the conditions changed */
1192             }
1193         }
1194     }
1195
1196     if (start_capture || list_link_layer_types) {
1197         /* We're supposed to do a live capture or get a list of link-layer
1198            types for a live capture device; if the user didn't specify an
1199            interface to use, pick a default. */
1200         status = capture_opts_default_iface_if_necessary(&global_capture_opts,
1201         ((prefs_p->capture_device) && (*prefs_p->capture_device != '\0')) ? get_if_name(prefs_p->capture_device) : NULL);
1202         if (status != 0) {
1203             exit(status);
1204         }
1205     }
1206
1207     if (list_link_layer_types) {
1208         /* Get the list of link-layer types for the capture devices. */
1209         if_capabilities_t *caps;
1210         guint i;
1211         interface_t device;
1212         for (i = 0; i < global_capture_opts.all_ifaces->len; i++) {
1213
1214             device = g_array_index(global_capture_opts.all_ifaces, interface_t, i);
1215             if (device.selected) {
1216 #if defined(HAVE_PCAP_CREATE)
1217                 caps = capture_get_if_capabilities(device.name, device.monitor_mode_supported, &err_str, main_window_update);
1218 #else
1219                 caps = capture_get_if_capabilities(device.name, FALSE, &err_str,main_window_update);
1220 #endif
1221                 if (caps == NULL) {
1222                     cmdarg_err("%s", err_str);
1223                     g_free(err_str);
1224                     exit(2);
1225                 }
1226             if (caps->data_link_types == NULL) {
1227                 cmdarg_err("The capture device \"%s\" has no data link types.", device.name);
1228                 exit(2);
1229             }
1230 #ifdef _WIN32
1231             create_console();
1232 #endif /* _WIN32 */
1233 #if defined(HAVE_PCAP_CREATE)
1234             capture_opts_print_if_capabilities(caps, device.name, device.monitor_mode_supported);
1235 #else
1236             capture_opts_print_if_capabilities(caps, device.name, FALSE);
1237 #endif
1238 #ifdef _WIN32
1239             destroy_console();
1240 #endif /* _WIN32 */
1241             free_if_capabilities(caps);
1242             }
1243         }
1244         exit(0);
1245     }
1246
1247     capture_opts_trim_snaplen(&global_capture_opts, MIN_PACKET_SIZE);
1248     capture_opts_trim_ring_num_files(&global_capture_opts);
1249 #endif /* HAVE_LIBPCAP */
1250
1251     /* Notify all registered modules that have had any of their preferences
1252        changed either from one of the preferences file or from the command
1253        line that their preferences have changed. */
1254     prefs_apply_all();
1255     wsApp->emitAppSignal(WiresharkApplication::PreferencesChanged);
1256
1257 #ifdef HAVE_LIBPCAP
1258     if ((global_capture_opts.num_selected == 0) &&
1259             (prefs.capture_device != NULL)) {
1260         guint i;
1261         interface_t device;
1262         for (i = 0; i < global_capture_opts.all_ifaces->len; i++) {
1263             device = g_array_index(global_capture_opts.all_ifaces, interface_t, i);
1264             if (!device.hidden && strcmp(device.display_name, prefs.capture_device) == 0) {
1265                 device.selected = TRUE;
1266                 global_capture_opts.num_selected++;
1267                 global_capture_opts.all_ifaces = g_array_remove_index(global_capture_opts.all_ifaces, i);
1268                 g_array_insert_val(global_capture_opts.all_ifaces, i, device);
1269                 break;
1270             }
1271         }
1272     }
1273 #endif
1274
1275     /* disabled protocols as per configuration file */
1276     if (gdp_path == NULL && dp_path == NULL) {
1277         set_disabled_protos_list();
1278     }
1279
1280     build_column_format_array(&CaptureFile::globalCapFile()->cinfo, prefs_p->num_cols, TRUE);
1281
1282     wsApp->setMonospaceFont(prefs.gui_qt_font_name);
1283
1284 ////////
1285
1286     /* Read the dynamic part of the recent file, as we have the gui now ready for
1287        it. */
1288     recent_read_dynamic(&rf_path, &rf_open_errno);
1289     if (rf_path != NULL && rf_open_errno != 0) {
1290         simple_dialog(ESD_TYPE_WARN, ESD_BTN_OK,
1291                       "Could not open recent file\n\"%s\": %s.",
1292                       rf_path, g_strerror(rf_open_errno));
1293     }
1294
1295     color_filters_enable(recent.packet_list_colorize);
1296
1297     g_log(NULL, G_LOG_LEVEL_DEBUG, "FIX: fetch recent color settings");
1298     color_filters_enable(TRUE);
1299
1300 ////////
1301
1302
1303 ////////
1304     color_filters_init();
1305
1306 ////////
1307
1308 #ifdef HAVE_LIBPCAP
1309     /* if the user didn't supply a capture filter, use the one to filter out remote connections like SSH */
1310     if (!start_capture && !global_capture_opts.default_options.cfilter) {
1311         global_capture_opts.default_options.cfilter = g_strdup(get_conn_cfilter());
1312     }
1313 #else /* HAVE_LIBPCAP */
1314     ////////
1315 #endif /* HAVE_LIBPCAP */
1316
1317 //    w->setEnabled(true);
1318     wsApp->allSystemsGo();
1319     g_log(LOG_DOMAIN_MAIN, G_LOG_LEVEL_INFO, "Wireshark is up and ready to go");
1320     SimpleDialog::displayQueuedMessages(main_w);
1321
1322     /* user could specify filename, or display filter, or both */
1323     if (!cf_name.isEmpty()) {
1324
1325         /* Open stat windows; we do so after creating the main window,
1326            to avoid Qt warnings, and after successfully opening the
1327            capture file, so we know we have something to compute stats
1328            on, and after registering all dissectors, so that MATE will
1329            have registered its field array and we can have a tap filter
1330            with one of MATE's late-registered fields as part of the
1331            filter. */
1332         start_requested_stats();
1333
1334         // XXX The GTK+ UI does error checking here.
1335         main_w->openCaptureFile(cf_name, read_filter, in_file_type);
1336         if (!dfilter.isEmpty())
1337             main_w->filterPackets(dfilter, false);
1338         if(go_to_packet != 0) {
1339             /* Jump to the specified frame number, kept for backward
1340                compatibility. */
1341             cf_goto_frame(CaptureFile::globalCapFile(), go_to_packet);
1342         }
1343     }
1344 #ifdef HAVE_LIBPCAP
1345     else {
1346         if (start_capture) {
1347             if (global_capture_opts.save_file != NULL) {
1348                 /* Save the directory name for future file dialogs. */
1349                 /* (get_dirname overwrites filename) */
1350                 gchar *s = get_dirname(g_strdup(global_capture_opts.save_file));
1351                 set_last_open_dir(s);
1352                 g_free(s);
1353             }
1354             /* "-k" was specified; start a capture. */
1355 //            show_main_window(FALSE);
1356             check_and_warn_user_startup(cf_name);
1357
1358             /* If no user interfaces were specified on the command line,
1359                copy the list of selected interfaces to the set of interfaces
1360                to use for this capture. */
1361             if (global_capture_opts.ifaces->len == 0)
1362                 collect_ifaces(&global_capture_opts);
1363             CaptureFile::globalCapFile()->window = main_w;
1364             if (capture_start(&global_capture_opts, main_w->captureSession(), main_window_update)) {
1365                 /* The capture started.  Open stat windows; we do so after creating
1366                    the main window, to avoid GTK warnings, and after successfully
1367                    opening the capture file, so we know we have something to compute
1368                    stats on, and after registering all dissectors, so that MATE will
1369                    have registered its field array and we can have a tap filter with
1370                    one of MATE's late-registered fields as part of the filter. */
1371                 start_requested_stats();
1372             }
1373         }
1374     /* if the user didn't supply a capture filter, use the one to filter out remote connections like SSH */
1375         if (!start_capture && !global_capture_opts.default_options.cfilter) {
1376             global_capture_opts.default_options.cfilter = g_strdup(get_conn_cfilter());
1377         }
1378     }
1379 #endif /* HAVE_LIBPCAP */
1380
1381     g_main_loop_new(NULL, FALSE);
1382     return wsApp->exec();
1383 }
1384
1385 /*
1386  * Editor modelines
1387  *
1388  * Local Variables:
1389  * c-basic-offset: 4
1390  * tab-width: 8
1391  * indent-tabs-mode: nil
1392  * End:
1393  *
1394  * ex: set shiftwidth=4 tabstop=8 expandtab:
1395  * :indentSize=4:tabSize=8:noTabs=true:
1396  */