clang -cc1 -cc1 -triple x86_64-pc-linux-gnu -analyze -disable-free -clear-ast-before-backend -disable-llvm-verifier -discard-value-names -main-file-name wireshark_main_window_slots.cpp -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=cplusplus -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 2 -fhalf-no-semantic-interposition -mframe-pointer=all -fmath-errno -ffp-contract=on -fno-rounding-math -ffloat16-excess-precision=fast -fbfloat16-excess-precision=fast -mconstructor-aliases -funwind-tables=2 -target-cpu x86-64 -tune-cpu generic -debugger-tuning=gdb -fdebug-compilation-dir=/builds/wireshark/wireshark/build -fcoverage-compilation-dir=/builds/wireshark/wireshark/build -resource-dir /usr/lib/llvm-18/lib/clang/18 -isystem /usr/include/glib-2.0 -isystem /usr/lib/x86_64-linux-gnu/glib-2.0/include -isystem /builds/wireshark/wireshark/build/ui/qt -isystem /builds/wireshark/wireshark/ui/qt -isystem /usr/include/x86_64-linux-gnu/qt6/QtWidgets -isystem /usr/include/x86_64-linux-gnu/qt6 -isystem /usr/include/x86_64-linux-gnu/qt6/QtCore -isystem /usr/lib/x86_64-linux-gnu/qt6/mkspecs/linux-g++ -isystem /usr/include/x86_64-linux-gnu/qt6/QtGui -isystem /usr/include/x86_64-linux-gnu/qt6/QtCore5Compat -isystem /usr/include/x86_64-linux-gnu/qt6/QtConcurrent -isystem /usr/include/x86_64-linux-gnu/qt6/QtPrintSupport -isystem /usr/include/x86_64-linux-gnu/qt6/QtMultimedia -isystem /usr/include/x86_64-linux-gnu/qt6/QtNetwork -isystem /usr/include/x86_64-linux-gnu/qt6/QtDBus -D G_DISABLE_DEPRECATED -D G_DISABLE_SINGLE_INCLUDES -D QT_CONCURRENT_LIB -D QT_CORE5COMPAT_LIB -D QT_CORE_LIB -D QT_DBUS_LIB -D QT_GUI_LIB -D QT_MULTIMEDIA_LIB -D QT_NETWORK_LIB -D QT_PRINTSUPPORT_LIB -D QT_WIDGETS_LIB -D WS_DEBUG -D WS_DEBUG_UTF_8 -I /builds/wireshark/wireshark/build/ui/qt/qtui_autogen/include -I /builds/wireshark/wireshark/build -I /builds/wireshark/wireshark -I /builds/wireshark/wireshark/include -internal-isystem /usr/lib/gcc/x86_64-linux-gnu/13/../../../../include/c++/13 -internal-isystem /usr/lib/gcc/x86_64-linux-gnu/13/../../../../include/x86_64-linux-gnu/c++/13 -internal-isystem /usr/lib/gcc/x86_64-linux-gnu/13/../../../../include/c++/13/backward -internal-isystem /usr/lib/llvm-18/lib/clang/18/include -internal-isystem /usr/local/include -internal-isystem /usr/lib/gcc/x86_64-linux-gnu/13/../../../../x86_64-linux-gnu/include -internal-externc-isystem /usr/include/x86_64-linux-gnu -internal-externc-isystem /include -internal-externc-isystem /usr/include -fmacro-prefix-map=/builds/wireshark/wireshark/= -fmacro-prefix-map=/builds/wireshark/wireshark/build/= -fmacro-prefix-map=../= -Wno-error=stringop-overflow= -Wno-error=deprecated-declarations -Wno-format-truncation -std=c++17 -fdeprecated-macro -ferror-limit 19 -fwrapv -fgnuc-version=4.2.1 -fskip-odr-check-in-gmf -fcxx-exceptions -fexceptions -fcolor-diagnostics -analyzer-output=html -dwarf-debug-flags /usr/lib/llvm-18/bin/clang --driver-mode=g++ -### --analyze -x c++ -D G_DISABLE_DEPRECATED -D G_DISABLE_SINGLE_INCLUDES -D QT_CONCURRENT_LIB -D QT_CORE5COMPAT_LIB -D QT_CORE_LIB -D QT_DBUS_LIB -D QT_GUI_LIB -D QT_MULTIMEDIA_LIB -D QT_NETWORK_LIB -D QT_PRINTSUPPORT_LIB -D QT_WIDGETS_LIB -D WS_DEBUG -D WS_DEBUG_UTF_8 -I /builds/wireshark/wireshark/build/ui/qt/qtui_autogen/include -I /builds/wireshark/wireshark/build -I /builds/wireshark/wireshark -I /builds/wireshark/wireshark/include -isystem /usr/include/glib-2.0 -isystem /usr/lib/x86_64-linux-gnu/glib-2.0/include -isystem /builds/wireshark/wireshark/build/ui/qt -isystem /builds/wireshark/wireshark/ui/qt -isystem /usr/include/x86_64-linux-gnu/qt6/QtWidgets -isystem /usr/include/x86_64-linux-gnu/qt6 -isystem /usr/include/x86_64-linux-gnu/qt6/QtCore -isystem /usr/lib/x86_64-linux-gnu/qt6/mkspecs/linux-g++ -isystem /usr/include/x86_64-linux-gnu/qt6/QtGui -isystem /usr/include/x86_64-linux-gnu/qt6/QtCore5Compat -isystem /usr/include/x86_64-linux-gnu/qt6/QtConcurrent -isystem /usr/include/x86_64-linux-gnu/qt6/QtPrintSupport -isystem /usr/include/x86_64-linux-gnu/qt6/QtMultimedia -isystem /usr/include/x86_64-linux-gnu/qt6/QtNetwork -isystem /usr/include/x86_64-linux-gnu/qt6/QtDBus -fno-strict-overflow -fexcess-precision=fast -Wno-error=stringop-overflow= -Wno-error=deprecated-declarations -Wno-format-truncation -fdiagnostics-color=always -fmacro-prefix-map=/builds/wireshark/wireshark/= -fmacro-prefix-map=/builds/wireshark/wireshark/build/= -fmacro-prefix-map=../= -std=c++17 -fPIC -fPIC /builds/wireshark/wireshark/ui/qt/wireshark_main_window_slots.cpp -o /builds/wireshark/wireshark/sbout/2024-08-11-100246-3329-1 -Xclang -analyzer-output=html -faddrsig -D__GCC_HAVE_DWARF2_CFI_ASM=1 -o /builds/wireshark/wireshark/sbout/2024-08-11-100246-3329-1 -x c++ /builds/wireshark/wireshark/ui/qt/wireshark_main_window_slots.cpp
1 | /* main_window_slots.cpp |
2 | * |
3 | * Wireshark - Network traffic analyzer |
4 | * By Gerald Combs <[emailprotected]> |
5 | * Copyright 1998 Gerald Combs |
6 | * |
7 | * SPDX-License-Identifier: GPL-2.0-or-later |
8 | */ |
9 | |
10 | #include <config.h> |
11 | |
12 | // Qt 5.5.0 + Visual C++ 2013 |
13 | #ifdef _MSC_VER |
14 | #pragma warning(push) |
15 | #pragma warning(disable:4996) |
16 | #endif |
17 | |
18 | #include "wireshark_main_window.h" |
19 | |
20 | /* |
21 | * The generated Ui_WiresharkMainWindow::setupUi() can grow larger than our configured limit, |
22 | * so turn off -Wframe-larger-than= for ui_wireshark_main_window.h. |
23 | */ |
24 | DIAG_OFF(frame-larger-than=)clang diagnostic push clang diagnostic ignored "-Wframe-larger-than="
|
25 | #include <ui_wireshark_main_window.h> |
26 | DIAG_ON(frame-larger-than=)clang diagnostic pop |
27 | |
28 | #ifdef _WIN32 |
29 | #include <windows.h> |
30 | #endif |
31 | |
32 | #include "ui/dissect_opts.h" |
33 | |
34 | #ifdef HAVE_LIBPCAP1 |
35 | #include "ui/capture.h" |
36 | #endif |
37 | |
38 | #include "ui/commandline.h" |
39 | |
40 | #include "ui/urls.h" |
41 | |
42 | #include "epan/color_filters.h" |
43 | #include "epan/export_object.h" |
44 | |
45 | #include "wsutil/file_util.h" |
46 | #include "wsutil/filesystem.h" |
47 | #include <wsutil/wslog.h> |
48 | #include <wsutil/ws_assert.h> |
49 | |
50 | #include "epan/addr_resolv.h" |
51 | #include "epan/column.h" |
52 | #include "epan/dfilter/dfilter-macro.h" |
53 | #include "epan/conversation_filter.h" |
54 | #include "epan/epan_dissect.h" |
55 | #include "epan/filter_expressions.h" |
56 | #include "epan/prefs.h" |
57 | #include "epan/plugin_if.h" |
58 | #include "epan/uat.h" |
59 | #include "epan/uat-int.h" |
60 | #include "epan/value_string.h" |
61 | |
62 | #ifdef HAVE_LUA1 |
63 | #include <epan/wslua/init_wslua.h> |
64 | #endif |
65 | |
66 | #include "ui/alert_box.h" |
67 | #ifdef HAVE_LIBPCAP1 |
68 | #include "ui/capture_ui_utils.h" |
69 | #endif |
70 | |
71 | #include "ui/capture_globals.h" |
72 | #include "ui/help_url.h" |
73 | #include "ui/main_statusbar.h" |
74 | #include "ui/preference_utils.h" |
75 | #include "ui/recent.h" |
76 | #include "ui/recent_utils.h" |
77 | #include "ui/ssl_key_export.h" |
78 | #include "ui/ws_ui_util.h" |
79 | #include "ui/all_files_wildcard.h" |
80 | #include "ui/qt/simple_dialog.h" |
81 | |
82 | #include <ui/qt/utils/variant_pointer.h> |
83 | #include <ui/qt/widgets/drag_drop_toolbar.h> |
84 | #include "ui/qt/widgets/wireshark_file_dialog.h" |
85 | |
86 | #ifdef HAVE_SOFTWARE_UPDATE |
87 | #include "ui/software_update.h" |
88 | #endif |
89 | |
90 | #include "about_dialog.h" |
91 | #include "bluetooth_att_server_attributes_dialog.h" |
92 | #include "bluetooth_devices_dialog.h" |
93 | #include "bluetooth_hci_summary_dialog.h" |
94 | #include "capture_file_dialog.h" |
95 | #include "capture_file_properties_dialog.h" |
96 | #ifdef HAVE_LIBPCAP1 |
97 | #include "capture_options_dialog.h" |
98 | #endif |
99 | #include <ui/qt/utils/color_utils.h> |
100 | #include "coloring_rules_dialog.h" |
101 | #include "conversation_dialog.h" |
102 | #include "conversation_colorize_action.h" |
103 | #include "conversation_hash_tables_dialog.h" |
104 | #include "enabled_protocols_dialog.h" |
105 | #include "decode_as_dialog.h" |
106 | #include <ui/qt/widgets/display_filter_edit.h> |
107 | #include "display_filter_expression_dialog.h" |
108 | #include "dissector_tables_dialog.h" |
109 | #include "endpoint_dialog.h" |
110 | #include "expert_info_dialog.h" |
111 | #include "export_object_action.h" |
112 | #include "export_object_dialog.h" |
113 | #include "export_pdu_dialog.h" |
114 | #include "extcap_options_dialog.h" |
115 | #include "file_set_dialog.h" |
116 | #include "filter_action.h" |
117 | #include "filter_dialog.h" |
118 | #include "firewall_rules_dialog.h" |
119 | #include "follow_stream_action.h" |
120 | #include "follow_stream_dialog.h" |
121 | #include "funnel_statistics.h" |
122 | #include "gsm_map_summary_dialog.h" |
123 | #include "iax2_analysis_dialog.h" |
124 | #include "interface_toolbar.h" |
125 | #include "io_graph_dialog.h" |
126 | #include <ui/qt/widgets/additional_toolbar.h> |
127 | #include "lbm_stream_dialog.h" |
128 | #include "lbm_lbtrm_transport_dialog.h" |
129 | #include "lbm_lbtru_transport_dialog.h" |
130 | #include "lte_mac_statistics_dialog.h" |
131 | #include "lte_rlc_statistics_dialog.h" |
132 | #include "lte_rlc_graph_dialog.h" |
133 | #include "main_application.h" |
134 | #include "manuf_dialog.h" |
135 | #include "mtp3_summary_dialog.h" |
136 | #include "multicast_statistics_dialog.h" |
137 | #include "packet_comment_dialog.h" |
138 | #include "packet_diagram.h" |
139 | #include "packet_dialog.h" |
140 | #include "packet_list.h" |
141 | #include "credentials_dialog.h" |
142 | #include "preferences_dialog.h" |
143 | #include "print_dialog.h" |
144 | #include "profile_dialog.h" |
145 | #include "protocol_hierarchy_dialog.h" |
146 | #include <ui/qt/utils/qt_ui_utils.h> |
147 | #include "resolved_addresses_dialog.h" |
148 | #include "rpc_service_response_time_dialog.h" |
149 | #include "rtp_stream_dialog.h" |
150 | #include "rtp_analysis_dialog.h" |
151 | #include "sctp_all_assocs_dialog.h" |
152 | #include "sctp_assoc_analyse_dialog.h" |
153 | #include "sctp_graph_dialog.h" |
154 | #include "sequence_dialog.h" |
155 | #include "show_packet_bytes_dialog.h" |
156 | #include "tlskeylog_launcher_dialog.h" |
157 | #include "stats_tree_dialog.h" |
158 | #include "strip_headers_dialog.h" |
159 | #include <ui/qt/utils/stock_icon.h> |
160 | #include "supported_protocols_dialog.h" |
161 | #include "tap_parameter_dialog.h" |
162 | #include "tcp_stream_dialog.h" |
163 | #include "time_shift_dialog.h" |
164 | #include "uat_dialog.h" |
165 | #include "voip_calls_dialog.h" |
166 | #include "wlan_statistics_dialog.h" |
167 | #include <ui/qt/widgets/wireless_timeline.h> |
168 | |
169 | #include <functional> |
170 | #include <QClipboard> |
171 | #include <QFileInfo> |
172 | #include <QMessageBox> |
173 | #include <QMetaObject> |
174 | #include <QToolBar> |
175 | #include <QDesktopServices> |
176 | #include <QUrl> |
177 | #include <QMutex> |
178 | |
179 | // XXX You must uncomment QT_WINEXTRAS_LIB lines in CMakeList.txt and |
180 | // cmakeconfig.h.in. |
181 | // #if defined(QT_WINEXTRAS_LIB) |
182 | // #include <QWinJumpList> |
183 | // #include <QWinJumpListCategory> |
184 | // #include <QWinJumpListItem> |
185 | // #endif |
186 | |
187 | // |
188 | // Public slots |
189 | // |
190 | |
191 | bool WiresharkMainWindow::openCaptureFile(QString cf_path, QString read_filter, unsigned int type, bool is_tempfile) |
192 | { |
193 | QString file_name = ""; |
194 | dfilter_t *rfcode = NULL__null; |
195 | df_error_t *df_err = NULL__null; |
196 | int err; |
197 | bool name_param; |
198 | bool ret = true; |
199 | |
200 | // was a file name given as function parameter? |
201 | name_param = !cf_path.isEmpty(); |
202 | |
203 | for (;;) { |
204 | |
205 | if (cf_path.isEmpty()) { |
206 | CaptureFileDialog open_dlg(this, capture_file_.capFile()); |
207 | |
208 | if (open_dlg.open(file_name, type, read_filter)) { |
209 | cf_path = file_name; |
210 | } else { |
211 | ret = false; |
212 | goto finish; |
213 | } |
214 | } else { |
215 | this->welcome_page_->getInterfaceFrame()->showRunOnFile(); |
216 | } |
217 | |
218 | // TODO detect call from "cf_read" -> "update_progress_dlg" |
219 | // ("capture_file_.capFile()->read_lock"), possibly queue opening the |
220 | // file and return early to avoid the warning in testCaptureFileClose. |
221 | |
222 | QString before_what(tr(" before opening another file")); |
223 | if (!testCaptureFileClose(before_what)) { |
224 | ret = false; |
225 | goto finish; |
226 | } |
227 | |
228 | if (dfilter_compile(qUtf8Printable(read_filter), &rfcode, &df_err)dfilter_compile_full(QtPrivate::asString(read_filter).toUtf8( ).constData(), &rfcode, &df_err, (1U << 1)|(1U << 2), __func__)) { |
229 | cf_set_rfcode(CaptureFile::globalCapFile(), rfcode); |
230 | } else { |
231 | /* Not valid. Tell the user, and go back and run the file |
232 | selection box again once they dismiss the alert. */ |
233 | //bad_dfilter_alert_box(top_level, read_filter->str); |
234 | QMessageBox::warning(this, tr("Invalid Display Filter"), |
235 | QString("The filter expression ") + |
236 | read_filter + |
237 | QString(" isn't a valid display filter. (") + |
238 | df_err->msg + QString(")."), |
239 | QMessageBox::Ok); |
240 | df_error_free(&df_err); |
241 | if (!name_param) { |
242 | // go back to the selection dialogue only if the file |
243 | // was selected from this dialogue |
244 | cf_path.clear(); |
245 | continue; |
246 | } |
247 | } |
248 | |
249 | /* Make the file name available via MainWindow */ |
250 | setMwFileName(cf_path); |
251 | |
252 | /* Try to open the capture file. This closes the current file if it succeeds. */ |
253 | CaptureFile::globalCapFile()->window = this; |
254 | if (cf_open(CaptureFile::globalCapFile(), qUtf8Printable(cf_path)QtPrivate::asString(cf_path).toUtf8().constData(), type, is_tempfile, &err) != CF_OK) { |
255 | /* We couldn't open it; don't dismiss the open dialog box, |
256 | just leave it around so that the user can, after they |
257 | dismiss the alert box popped up for the open error, |
258 | try again. */ |
259 | CaptureFile::globalCapFile()->window = NULL__null; |
260 | dfilter_free(rfcode); |
261 | cf_path.clear(); |
262 | continue; |
263 | } |
264 | |
265 | switch (cf_read(CaptureFile::globalCapFile(), /*reloading=*/false)) { |
266 | case CF_READ_OK: |
267 | case CF_READ_ERROR: |
268 | /* Just because we got an error, that doesn't mean we were unable |
269 | to read any of the file; we handle what we could get from the |
270 | file. */ |
271 | break; |
272 | |
273 | case CF_READ_ABORTED: |
274 | /* The user bailed out of re-reading the capture file; the |
275 | capture file has been closed - just free the capture file name |
276 | string and return (without changing the last containing |
277 | directory). */ |
278 | capture_file_.setCapFile(NULL__null); |
279 | ret = false; |
280 | goto finish; |
281 | } |
282 | break; |
283 | } |
284 | |
285 | if (!is_tempfile) { |
286 | mainApp->setLastOpenDirFromFilename(cf_path); |
287 | } |
288 | |
289 | main_ui_->statusBar->showExpert(); |
290 | |
291 | finish: |
292 | #ifdef HAVE_LIBPCAP1 |
293 | if (global_commandline_info.quit_after_cap) |
294 | exit(0); |
295 | #endif |
296 | return ret; |
297 | } |
298 | |
299 | void WiresharkMainWindow::filterPackets(QString new_filter, bool force) |
300 | { |
301 | cf_status_t cf_status; |
302 | |
303 | cf_status = cf_filter_packets(CaptureFile::globalCapFile(), new_filter.toUtf8().data(), force); |
304 | |
305 | if (cf_status == CF_OK) { |
306 | if (new_filter.length() > 0) { |
307 | int index = df_combo_box_->findText(new_filter); |
308 | if (index == -1) { |
309 | df_combo_box_->insertItem(0, new_filter); |
310 | df_combo_box_->setCurrentIndex(0); |
311 | } else { |
312 | df_combo_box_->setCurrentIndex(index); |
313 | } |
314 | } else { |
315 | df_combo_box_->lineEdit()->clear(); |
316 | } |
317 | // Only after the display filter has been updated, |
318 | // disable the arrow button |
319 | emit displayFilterSuccess(true); |
320 | } else { |
321 | emit displayFilterSuccess(false); |
322 | } |
323 | } |
324 | |
325 | void WiresharkMainWindow::layoutToolbars() |
326 | { |
327 | Qt::ToolButtonStyle tbstyle = Qt::ToolButtonIconOnly; |
328 | switch (prefs.gui_toolbar_main_style) { |
329 | case TB_STYLE_TEXT1: |
330 | tbstyle = Qt::ToolButtonTextOnly; |
331 | break; |
332 | case TB_STYLE_BOTH2: |
333 | tbstyle = Qt::ToolButtonTextUnderIcon; |
334 | break; |
335 | } |
336 | |
337 | main_ui_->mainToolBar->setToolButtonStyle(tbstyle); |
338 | |
339 | main_ui_->mainToolBar->setVisible(recent.main_toolbar_show); |
340 | main_ui_->displayFilterToolBar->setVisible(recent.filter_toolbar_show); |
341 | #if defined(HAVE_LIBNL1) && defined(HAVE_NL802111) |
342 | main_ui_->wirelessToolBar->setVisible(recent.wireless_toolbar_show); |
343 | #endif |
344 | main_ui_->statusBar->setVisible(recent.statusbar_show); |
345 | |
346 | foreach(QAction *action, main_ui_->menuInterfaceToolbars->actions())for (auto _container_346 = QtPrivate::qMakeForeachContainer(main_ui_ ->menuInterfaceToolbars->actions()); _container_346.i != _container_346.e; ++_container_346.i) if (QAction *action = * _container_346.i; false) {} else { |
347 | QToolBar *toolbar = action->data().value<QToolBar *>(); |
348 | if (g_list_find_custom(recent.interface_toolbars, action->text().toUtf8(), (GCompareFunc)strcmp)) { |
349 | toolbar->setVisible(true); |
350 | } else { |
351 | toolbar->setVisible(false); |
352 | } |
353 | } |
354 | |
355 | QList<QToolBar *> toolbars = findChildren<QToolBar *>(); |
356 | foreach(QToolBar *bar, toolbars)for (auto _container_356 = QtPrivate::qMakeForeachContainer(toolbars ); _container_356.i != _container_356.e; ++_container_356.i) if (QToolBar *bar = *_container_356.i; false) {} else { |
357 | AdditionalToolBar *iftoolbar = dynamic_cast<AdditionalToolBar *>(bar); |
358 | if (iftoolbar) { |
359 | bool visible = false; |
360 | if (g_list_find_custom(recent.gui_additional_toolbars, qUtf8Printable(iftoolbar->menuName())QtPrivate::asString(iftoolbar->menuName()).toUtf8().constData (), (GCompareFunc)strcmp)) |
361 | visible = true; |
362 | |
363 | iftoolbar->setVisible(visible); |
364 | |
365 | } |
366 | } |
367 | } |
368 | |
369 | static const char* layout_icons[] = { |
370 | NULL__null, |
371 | "x-reset-layout_5", |
372 | "x-reset-layout_2", |
373 | "x-reset-layout_1", |
374 | "x-reset-layout_4", |
375 | "x-reset-layout_3", |
376 | "x-reset-layout_6" |
377 | }; |
378 | |
379 | void WiresharkMainWindow::updatePreferenceActions() |
380 | { |
381 | main_ui_->actionViewPacketList->setEnabled(prefs_has_layout_pane_content(layout_pane_content_plist)); |
382 | main_ui_->actionViewPacketDetails->setEnabled(prefs_has_layout_pane_content(layout_pane_content_pdetails)); |
383 | main_ui_->actionViewPacketBytes->setEnabled(prefs_has_layout_pane_content(layout_pane_content_pbytes)); |
384 | main_ui_->actionViewPacketDiagram->setEnabled(prefs_has_layout_pane_content(layout_pane_content_pdiagram)); |
385 | |
386 | main_ui_->actionViewNameResolutionPhysical->setChecked(gbl_resolv_flags.mac_name); |
387 | main_ui_->actionViewNameResolutionNetwork->setChecked(gbl_resolv_flags.network_name); |
388 | main_ui_->actionViewNameResolutionTransport->setChecked(gbl_resolv_flags.transport_name); |
389 | |
390 | if (prefs.gui_layout_type > 0) |
391 | main_ui_->actionViewResetLayout->setIcon(StockIcon(layout_icons[prefs.gui_layout_type])); |
392 | } |
393 | |
394 | void WiresharkMainWindow::updateRecentActions() |
395 | { |
396 | main_ui_->actionViewMainToolbar->setChecked(recent.main_toolbar_show); |
397 | main_ui_->actionViewFilterToolbar->setChecked(recent.filter_toolbar_show); |
398 | main_ui_->actionViewWirelessToolbar->setChecked(recent.wireless_toolbar_show); |
399 | main_ui_->actionViewStatusBar->setChecked(recent.statusbar_show); |
400 | main_ui_->actionViewPacketList->setChecked(recent.packet_list_show && prefs_has_layout_pane_content(layout_pane_content_plist)); |
401 | main_ui_->actionViewPacketDetails->setChecked(recent.tree_view_show && prefs_has_layout_pane_content(layout_pane_content_pdetails)); |
402 | main_ui_->actionViewPacketBytes->setChecked(recent.byte_view_show && prefs_has_layout_pane_content(layout_pane_content_pbytes)); |
403 | main_ui_->actionViewPacketDiagram->setChecked(recent.packet_diagram_show && prefs_has_layout_pane_content(layout_pane_content_pdiagram)); |
404 | |
405 | foreach(QAction *action, main_ui_->menuInterfaceToolbars->actions())for (auto _container_405 = QtPrivate::qMakeForeachContainer(main_ui_ ->menuInterfaceToolbars->actions()); _container_405.i != _container_405.e; ++_container_405.i) if (QAction *action = * _container_405.i; false) {} else { |
406 | if (g_list_find_custom(recent.interface_toolbars, action->text().toUtf8(), (GCompareFunc)strcmp)) { |
407 | action->setChecked(true); |
408 | } else { |
409 | action->setChecked(false); |
410 | } |
411 | } |
412 | |
413 | foreach(QAction * action, main_ui_->menuAdditionalToolbars->actions())for (auto _container_413 = QtPrivate::qMakeForeachContainer(main_ui_ ->menuAdditionalToolbars->actions()); _container_413.i != _container_413.e; ++_container_413.i) if (QAction * action = *_container_413.i; false) {} else { |
414 | ext_toolbar_t * toolbar = VariantPointer<ext_toolbar_t>::asPtr(action->data()); |
415 | bool checked = false; |
416 | if (toolbar && g_list_find_custom(recent.gui_additional_toolbars, toolbar->name, (GCompareFunc)strcmp)) |
417 | checked = true; |
418 | |
419 | action->setChecked(checked); |
420 | } |
421 | |
422 | foreach(QAction* tda, td_actions.keys())for (auto _container_422 = QtPrivate::qMakeForeachContainer(td_actions .keys()); _container_422.i != _container_422.e; ++_container_422 .i) if (QAction* tda = *_container_422.i; false) {} else { |
423 | if (recent.gui_time_format == td_actions[tda]) { |
424 | tda->setChecked(true); |
425 | } |
426 | } |
427 | foreach(QAction* tpa, tp_actions.keys())for (auto _container_427 = QtPrivate::qMakeForeachContainer(tp_actions .keys()); _container_427.i != _container_427.e; ++_container_427 .i) if (QAction* tpa = *_container_427.i; false) {} else { |
428 | if (recent.gui_time_precision == tp_actions[tpa]) { |
429 | tpa->setChecked(true); |
430 | break; |
431 | } |
432 | } |
433 | main_ui_->actionViewTimeDisplaySecondsWithHoursAndMinutes->setChecked(recent.gui_seconds_format == TS_SECONDS_HOUR_MIN_SEC); |
434 | |
435 | main_ui_->actionViewColorizePacketList->setChecked(recent.packet_list_colorize); |
436 | |
437 | main_ui_->actionGoAutoScroll->setChecked(recent.capture_auto_scroll); |
438 | } |
439 | |
440 | // Don't connect to this directly. Connect to or emit filterAction(...) instead. |
441 | void WiresharkMainWindow::queuedFilterAction(QString action_filter, FilterAction::Action action, FilterAction::ActionType type) |
442 | { |
443 | QString cur_filter, new_filter; |
444 | |
445 | if (!df_combo_box_) return; |
446 | cur_filter = df_combo_box_->lineEdit()->text(); |
447 | |
448 | switch (type) { |
449 | case FilterAction::ActionTypePlain: |
450 | new_filter = action_filter; |
451 | break; |
452 | case FilterAction::ActionTypeAnd: |
453 | if (cur_filter.length()) { |
454 | new_filter = "(" + cur_filter + ") && (" + action_filter + ")"; |
455 | } |
456 | else { |
457 | new_filter = action_filter; |
458 | } |
459 | break; |
460 | case FilterAction::ActionTypeOr: |
461 | if (cur_filter.length()) { |
462 | new_filter = "(" + cur_filter + ") || (" + action_filter + ")"; |
463 | } else { |
464 | new_filter = action_filter; |
465 | } |
466 | break; |
467 | case FilterAction::ActionTypeNot: |
468 | new_filter = "!(" + action_filter + ")"; |
469 | break; |
470 | case FilterAction::ActionTypeAndNot: |
471 | if (cur_filter.length()) { |
472 | new_filter = "(" + cur_filter + ") && !(" + action_filter + ")"; |
473 | } else { |
474 | new_filter = "!(" + action_filter + ")"; |
475 | } |
476 | break; |
477 | case FilterAction::ActionTypeOrNot: |
478 | if (cur_filter.length()) { |
479 | new_filter = "(" + cur_filter + ") || !(" + action_filter + ")"; |
480 | } else { |
481 | new_filter = "!(" + action_filter + ")"; |
482 | } |
483 | break; |
484 | default: |
485 | ws_assert_not_reached()ws_log_fatal_full("", LOG_LEVEL_ERROR, "ui/qt/wireshark_main_window_slots.cpp" , 485, __func__, "assertion \"not reached\" failed"); |
486 | break; |
487 | } |
488 | |
489 | switch (action) { |
490 | case FilterAction::ActionApply: |
491 | df_combo_box_->lineEdit()->setText(new_filter); |
492 | df_combo_box_->applyDisplayFilter(); |
493 | break; |
494 | case FilterAction::ActionColorize: |
495 | colorizeWithFilter(new_filter.toUtf8()); |
496 | break; |
497 | case FilterAction::ActionCopy: |
498 | mainApp->clipboard()->setText(new_filter); |
499 | break; |
500 | case FilterAction::ActionFind: |
501 | main_ui_->searchFrame->findFrameWithFilter(new_filter); |
502 | break; |
503 | case FilterAction::ActionPrepare: |
504 | df_combo_box_->lineEdit()->setText(new_filter); |
505 | df_combo_box_->lineEdit()->setFocus(); |
506 | break; |
507 | case FilterAction::ActionWebLookup: |
508 | { |
509 | QString url = QString("https://www.google.com/search?q=") + new_filter; |
510 | QDesktopServices::openUrl(QUrl(url)); |
511 | break; |
512 | } |
513 | default: |
514 | ws_assert_not_reached()ws_log_fatal_full("", LOG_LEVEL_ERROR, "ui/qt/wireshark_main_window_slots.cpp" , 514, __func__, "assertion \"not reached\" failed"); |
515 | break; |
516 | } |
517 | } |
518 | |
519 | // Capture callbacks |
520 | |
521 | #ifdef HAVE_LIBPCAP1 |
522 | void WiresharkMainWindow::captureCapturePrepared(capture_session *session) { |
523 | setTitlebarForCaptureInProgress(); |
524 | setWindowIcon(mainApp->captureIcon()); |
525 | pushLiveCaptureInProgress(); |
526 | |
527 | /* Disable menu items that make no sense if you're currently running |
528 | a capture. */ |
529 | bool handle_toolbars = (session->session_will_restart ? false : true); |
530 | setForCaptureInProgress(true, handle_toolbars, session->capture_opts->ifaces); |
531 | // set_capture_if_dialog_for_capture_in_progress(true); |
532 | |
533 | // /* Don't set up main window for a capture file. */ |
534 | // main_set_for_capture_file(false); |
535 | showCapture(); |
536 | } |
537 | |
538 | void WiresharkMainWindow::captureCaptureUpdateStarted(capture_session *session) { |
539 | |
540 | /* We've done this in "prepared" above, but it will be cleared while |
541 | switching to the next multiple file. */ |
542 | setTitlebarForCaptureInProgress(); |
543 | setWindowIcon(mainApp->captureIcon()); |
544 | pushLiveCaptureInProgress(); |
545 | |
546 | bool handle_toolbars = (session->session_will_restart ? false : true); |
547 | setForCaptureInProgress(true, handle_toolbars, session->capture_opts->ifaces); |
548 | |
549 | setForCapturedPackets(true); |
550 | } |
551 | |
552 | void WiresharkMainWindow::captureCaptureUpdateFinished(capture_session *session) { |
553 | |
554 | /* The capture isn't stopping any more - it's stopped. */ |
555 | capture_stopping_ = false; |
556 | |
557 | /* Update the main window as appropriate */ |
558 | updateForUnsavedChanges(); |
559 | setTitlebarForCaptureFile(); |
560 | |
561 | /* Enable menu items that make sense if you're not currently running |
562 | a capture. */ |
563 | bool handle_toolbars = (session->session_will_restart ? false : true); |
564 | setForCaptureInProgress(false, handle_toolbars); |
565 | setMenusForCaptureFile(); |
566 | |
567 | setWindowIcon(mainApp->normalIcon()); |
568 | popLiveCaptureInProgress(); |
569 | |
570 | if (global_commandline_info.quit_after_cap) { |
571 | // Command line asked us to quit after capturing. |
572 | // Don't pop up a dialog to ask for unsaved files etc. |
573 | exit(0); |
574 | } |
575 | } |
576 | |
577 | void WiresharkMainWindow::captureCaptureFixedFinished(capture_session *) { |
578 | |
579 | /* The capture isn't stopping any more - it's stopped. */ |
580 | capture_stopping_ = false; |
581 | setTitlebarForCaptureFile(); |
582 | |
583 | /* Enable menu items that make sense if you're not currently running |
584 | a capture. */ |
585 | setForCaptureInProgress(false); |
586 | /* There isn't a real capture_file structure yet, so just force disabling |
587 | menu options. They will "refresh" when the capture file is reloaded to |
588 | display packets */ |
589 | setMenusForCaptureFile(true); |
590 | |
591 | setWindowIcon(mainApp->normalIcon()); |
592 | popLiveCaptureInProgress(); |
593 | |
594 | if (global_commandline_info.quit_after_cap) { |
595 | // Command line asked us to quit after capturing. |
596 | // Don't pop up a dialog to ask for unsaved files etc. |
597 | exit(0); |
598 | } |
599 | } |
600 | |
601 | void WiresharkMainWindow::captureCaptureFailed(capture_session *) { |
602 | /* Capture isn't stopping any more. */ |
603 | capture_stopping_ = false; |
604 | setTitlebarForCaptureFile(); |
605 | setForCaptureInProgress(false); |
606 | showWelcome(); |
607 | |
608 | // Reset expert information indicator |
609 | main_ui_->statusBar->captureFileClosing(); |
610 | mainApp->popStatus(WiresharkApplication::FileStatus); |
611 | |
612 | setWindowIcon(mainApp->normalIcon()); |
613 | popLiveCaptureInProgress(); |
614 | |
615 | if (global_commandline_info.quit_after_cap) { |
616 | // Command line asked us to quit after capturing. |
617 | // Don't pop up a dialog to ask for unsaved files etc. |
618 | exit(0); |
619 | } |
620 | } |
621 | #endif // HAVE_LIBPCAP |
622 | |
623 | // Callbacks from cfile.c and file.c via CaptureFile::captureFileCallback |
624 | |
625 | void WiresharkMainWindow::captureEventHandler(CaptureEvent ev) |
626 | { |
627 | switch (ev.captureContext()) { |
| 1 | Control jumps to 'case File:' at line 629 | |
|
628 | |
629 | case CaptureEvent::File: |
630 | switch (ev.eventType()) { |
| 2 | | Control jumps to 'case Closed:' at line 637 | |
|
631 | case CaptureEvent::Opened: |
632 | captureFileOpened(); |
633 | break; |
634 | case CaptureEvent::Closing: |
635 | captureFileClosing(); |
636 | break; |
637 | case CaptureEvent::Closed: |
638 | captureFileClosed(); |
| 3 | | Calling 'WiresharkMainWindow::captureFileClosed' | |
|
639 | break; |
640 | case CaptureEvent::Started: |
641 | captureFileReadStarted(tr("Loading")); |
642 | break; |
643 | case CaptureEvent::Finished: |
644 | captureFileReadFinished(); |
645 | break; |
646 | default: |
647 | break; |
648 | } |
649 | break; |
650 | |
651 | case CaptureEvent::Reload: |
652 | switch (ev.eventType()) { |
653 | case CaptureEvent::Started: |
654 | captureFileReadStarted(tr("Reloading")); |
655 | break; |
656 | case CaptureEvent::Finished: |
657 | captureFileReadFinished(); |
658 | break; |
659 | default: |
660 | break; |
661 | } |
662 | break; |
663 | |
664 | case CaptureEvent::Rescan: |
665 | switch (ev.eventType()) { |
666 | case CaptureEvent::Started: |
667 | setMenusForCaptureFile(true); |
668 | captureFileReadStarted(tr("Rescanning")); |
669 | break; |
670 | case CaptureEvent::Finished: |
671 | captureFileReadFinished(); |
672 | break; |
673 | default: |
674 | break; |
675 | } |
676 | break; |
677 | |
678 | case CaptureEvent::Retap: |
679 | switch (ev.eventType()) { |
680 | case CaptureEvent::Started: |
681 | freeze(); |
682 | break; |
683 | case CaptureEvent::Finished: |
684 | thaw(); |
685 | break; |
686 | case CaptureEvent::Flushed: |
687 | draw_tap_listeners(false); |
688 | break; |
689 | default: |
690 | break; |
691 | } |
692 | break; |
693 | |
694 | case CaptureEvent::Merge: |
695 | switch (ev.eventType()) { |
696 | case CaptureEvent::Started: |
697 | mainApp->popStatus(WiresharkApplication::FileStatus); |
698 | mainApp->pushStatus(WiresharkApplication::FileStatus, tr("Merging files."), QString()); |
699 | break; |
700 | case CaptureEvent::Finished: |
701 | mainApp->popStatus(WiresharkApplication::FileStatus); |
702 | break; |
703 | default: |
704 | break; |
705 | } |
706 | break; |
707 | |
708 | case CaptureEvent::Save: |
709 | switch (ev.eventType()) { |
710 | case CaptureEvent::Started: |
711 | { |
712 | QFileInfo file_info(ev.filePath()); |
713 | mainApp->popStatus(WiresharkApplication::FileStatus); |
714 | mainApp->pushStatus(WiresharkApplication::FileStatus, tr("Saving %1…").arg(file_info.fileName())); |
715 | break; |
716 | } |
717 | default: |
718 | break; |
719 | } |
720 | break; |
721 | |
722 | #ifdef HAVE_LIBPCAP1 |
723 | case CaptureEvent::Capture: |
724 | switch (ev.eventType()) { |
725 | case CaptureEvent::Prepared: |
726 | captureCapturePrepared(ev.capSession()); |
727 | break; |
728 | case CaptureEvent::Stopping: |
729 | capture_stopping_ = true; |
730 | setMenusForCaptureStopping(); |
731 | break; |
732 | case CaptureEvent::Failed: |
733 | captureCaptureFailed(ev.capSession()); |
734 | default: |
735 | break; |
736 | } |
737 | break; |
738 | |
739 | case CaptureEvent::Update: |
740 | switch (ev.eventType()) { |
741 | case CaptureEvent::Started: |
742 | captureCaptureUpdateStarted(ev.capSession()); |
743 | break; |
744 | case CaptureEvent::Finished: |
745 | captureCaptureUpdateFinished(ev.capSession()); |
746 | break; |
747 | default: |
748 | break; |
749 | } |
750 | break; |
751 | |
752 | case CaptureEvent::Fixed: |
753 | switch (ev.eventType()) { |
754 | case CaptureEvent::Finished: |
755 | captureCaptureFixedFinished(ev.capSession()); |
756 | break; |
757 | default: |
758 | break; |
759 | } |
760 | break; |
761 | #endif |
762 | } |
763 | } |
764 | |
765 | void WiresharkMainWindow::captureFileOpened() { |
766 | if (capture_file_.window() != this) return; |
767 | |
768 | file_set_dialog_->fileOpened(capture_file_.capFile()); |
769 | setMenusForFileSet(true); |
770 | emit setCaptureFile(capture_file_.capFile()); |
771 | } |
772 | |
773 | void WiresharkMainWindow::captureFileReadStarted(const QString &action) { |
774 | // tap_param_dlg_update(); |
775 | |
776 | /* Set up main window for a capture file. */ |
777 | // main_set_for_capture_file(true); |
778 | |
779 | mainApp->popStatus(WiresharkApplication::FileStatus); |
780 | QString msg = QString(tr("%1: %2")).arg(action).arg(capture_file_.fileName()); |
781 | QString msgtip = QString(); |
782 | mainApp->pushStatus(WiresharkApplication::FileStatus, msg, msgtip); |
783 | showCapture(); |
784 | main_ui_->actionAnalyzeReloadLuaPlugins->setEnabled(false); |
785 | main_ui_->wirelessTimelineWidget->captureFileReadStarted(capture_file_.capFile()); |
786 | } |
787 | |
788 | void WiresharkMainWindow::captureFileReadFinished() { |
789 | if (!capture_file_.capFile()->is_tempfile && capture_file_.capFile()->filename) { |
790 | /* Add this filename to the list of recent files in the "Recent Files" submenu */ |
791 | add_menu_recent_capture_file(capture_file_.capFile()->filename, false); |
792 | |
793 | /* Remember folder for next Open dialog and save it in recent */ |
794 | mainApp->setLastOpenDirFromFilename(capture_file_.capFile()->filename); |
795 | } |
796 | |
797 | /* Update the appropriate parts of the main window. */ |
798 | updateForUnsavedChanges(); |
799 | |
800 | /* enable wireless timeline if capture allows it */ |
801 | main_ui_->wirelessTimelineWidget->captureFileReadFinished(); |
802 | |
803 | /* Enable menu items that make sense if you have some captured packets. */ |
804 | setForCapturedPackets(true); |
805 | |
806 | main_ui_->statusBar->setFileName(capture_file_); |
807 | main_ui_->actionAnalyzeReloadLuaPlugins->setEnabled(true); |
808 | |
809 | packet_list_->captureFileReadFinished(); |
810 | |
811 | emit setDissectedCaptureFile(capture_file_.capFile()); |
812 | } |
813 | |
814 | void WiresharkMainWindow::captureFileClosing() { |
815 | setMenusForCaptureFile(true); |
816 | setTitlebarForCaptureFile(); |
817 | setForCapturedPackets(false); |
818 | setForCaptureInProgress(false); |
819 | |
820 | // Reset expert information indicator |
821 | main_ui_->statusBar->captureFileClosing(); |
822 | main_ui_->searchFrame->animatedHide(); |
823 | main_ui_->goToFrame->animatedHide(); |
824 | // gtk_widget_show(expert_info_none); |
825 | emit setCaptureFile(NULL__null); |
826 | emit setDissectedCaptureFile(NULL__null); |
827 | } |
828 | |
829 | void WiresharkMainWindow::captureFileClosed() { |
830 | packets_bar_update(); |
831 | |
832 | file_set_dialog_->fileClosed(); |
833 | setMenusForFileSet(false); |
834 | setWindowModified(false); |
835 | |
836 | // Reset expert information indicator |
837 | main_ui_->statusBar->captureFileClosing(); |
838 | mainApp->popStatus(WiresharkApplication::FileStatus); |
839 | |
840 | setWSWindowTitle(); |
841 | setWindowIcon(mainApp->normalIcon()); |
842 | setMenusForSelectedPacket(); |
| 4 | | Calling 'WiresharkMainWindow::setMenusForSelectedPacket' | |
|
843 | setMenusForSelectedTreeRow(); |
844 | |
845 | #ifdef HAVE_LIBPCAP1 |
846 | if (!global_capture_opts.multi_files_on) |
847 | showWelcome(); |
848 | #endif |
849 | } |
850 | |
851 | // |
852 | // Private slots |
853 | // |
854 | |
855 | // ui/gtk/capture_dlg.c:start_capture_confirmed |
856 | |
857 | void WiresharkMainWindow::startCapture() { |
858 | startCapture(QStringList()); |
859 | } |
860 | |
861 | void WiresharkMainWindow::startCapture(QStringList interfaces) { |
862 | #ifdef HAVE_LIBPCAP1 |
863 | interface_options *interface_opts; |
864 | unsigned i; |
865 | interface_t *device; |
866 | bool can_start_capture = true; |
867 | |
868 | if (interfaces.count() > 0) { |
869 | global_capture_opts.num_selected = 0; |
870 | for (i = 0; i < global_capture_opts.all_ifaces->len; i++) { |
871 | device = &g_array_index(global_capture_opts.all_ifaces, interface_t, i)(((interface_t*) (void *) (global_capture_opts.all_ifaces)-> data) [(i)]); |
872 | |
873 | if (interfaces.contains(device->name)) { |
874 | device->selected = true; |
875 | global_capture_opts.num_selected++; |
876 | } |
877 | else { |
878 | device->selected = false; |
879 | } |
880 | } |
881 | } |
882 | |
883 | /* did the user ever select a capture interface before? */ |
884 | if (global_capture_opts.num_selected == 0) { |
885 | QString msg = QString(tr("No interface selected.")); |
886 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, msg); |
887 | main_ui_->actionCaptureStart->setChecked(false); |
888 | return; |
889 | } |
890 | |
891 | for (i = 0; i < global_capture_opts.all_ifaces->len; i++) { |
892 | device = &g_array_index(global_capture_opts.all_ifaces, interface_t, i)(((interface_t*) (void *) (global_capture_opts.all_ifaces)-> data) [(i)]); |
893 | if (device->selected && (device->if_info.type == IF_EXTCAP)) { |
894 | /* device is EXTCAP and is selected. Check if all mandatory |
895 | * settings are set. |
896 | */ |
897 | if (extcap_requires_configuration(device->name)) |
898 | { |
899 | /* Request opening of extcap options dialog */ |
900 | QString device_name(device->name); |
901 | emit showExtcapOptions(device_name, false); |
902 | /* Cancel start of capture */ |
903 | can_start_capture = false; |
904 | } |
905 | } |
906 | } |
907 | |
908 | /* If some of extcap was not configured, do not start with the capture */ |
909 | if (!can_start_capture) { |
910 | QString msg = QString(tr("Configure all extcaps before start of capture.")); |
911 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, msg); |
912 | main_ui_->actionCaptureStart->setChecked(false); |
913 | return; |
914 | } |
915 | |
916 | // Ideally we should have disabled the start capture |
917 | // toolbar buttons and menu items. This may not be the |
918 | // case, e.g. with QtMacExtras. |
919 | if (!capture_filter_valid_) { |
920 | QString msg = QString(tr("Invalid capture filter.")); |
921 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, msg); |
922 | main_ui_->actionCaptureStart->setChecked(false); |
923 | return; |
924 | } |
925 | |
926 | showCapture(); |
927 | |
928 | /* XXX - we might need to init other pref data as well... */ |
929 | main_ui_->actionGoAutoScroll->setChecked(recent.capture_auto_scroll); |
930 | |
931 | /* XXX - can this ever happen? */ |
932 | if (cap_session_.state != CAPTURE_STOPPED) |
933 | return; |
934 | |
935 | /* close the currently loaded capture file */ |
936 | cf_close((capture_file *)cap_session_.cf); |
937 | |
938 | /* Copy the selected interfaces to the set of interfaces to use for |
939 | this capture. */ |
940 | collect_ifaces(&global_capture_opts); |
941 | |
942 | CaptureFile::globalCapFile()->window = this; |
943 | info_data_.ui.ui = this; |
944 | if (capture_start(&global_capture_opts, NULL__null, &cap_session_, &info_data_, |
945 | main_window_update)) { |
946 | /* The capture succeeded, which means the capture filter syntax is |
947 | valid; add this capture filter to the recent capture filter list. */ |
948 | QByteArray filter_ba; |
949 | for (i = 0; i < global_capture_opts.ifaces->len; i++) { |
950 | interface_opts = &g_array_index(global_capture_opts.ifaces, interface_options, i)(((interface_options*) (void *) (global_capture_opts.ifaces)-> data) [(i)]); |
951 | if (interface_opts->cfilter) { |
952 | recent_add_cfilter(interface_opts->name, interface_opts->cfilter); |
953 | if (filter_ba.isEmpty()) { |
954 | filter_ba = interface_opts->cfilter; |
955 | } else { |
956 | /* Not the first selected interface; is its capture filter |
957 | the same as the one the other interfaces we've looked |
958 | at have? */ |
959 | /* XXX: GCC 12.1 has a bogus warning at -O2 and higher |
960 | * even though the isEmpty() check guarantees that |
961 | * filter_ba.constData() is never NULL or empty. |
962 | */ |
963 | #if WS_IS_AT_LEAST_GNUC_VERSION(12,1)(4 > (12) || (4 == (12) && 2 >= (1))) |
964 | DIAG_OFF(stringop-overread)clang diagnostic push clang diagnostic ignored "-Wstringop-overread"
|
965 | #endif |
966 | if (strcmp(interface_opts->cfilter, filter_ba.constData()) != 0) { |
967 | #if WS_IS_AT_LEAST_GNUC_VERSION(12,1)(4 > (12) || (4 == (12) && 2 >= (1))) |
968 | DIAG_ON(stringop-overread)clang diagnostic pop |
969 | #endif |
970 | /* No, so not all selected interfaces have the same capture |
971 | filter. */ |
972 | filter_ba.clear(); |
973 | } |
974 | } |
975 | } |
976 | } |
977 | if (!filter_ba.isEmpty()) { |
978 | recent_add_cfilter(NULL__null, filter_ba.constData()); |
979 | } |
980 | } else { |
981 | CaptureFile::globalCapFile()->window = NULL__null; |
982 | } |
983 | #else // HAVE_LIBPCAP |
984 | Q_UNUSED(interfaces)(void)interfaces; |
985 | #endif // HAVE_LIBPCAP |
986 | } |
987 | |
988 | void WiresharkMainWindow::pushLiveCaptureInProgress() { |
989 | #ifdef HAVE_LIBPCAP1 |
990 | capture_options *capture_opts = cap_session_.capture_opts; |
991 | GString *interface_names; |
992 | |
993 | /* Add "interface name<live capture in progress>" on main status bar */ |
994 | interface_names = get_iface_list_string(capture_opts, 0); |
995 | if (strlen(interface_names->str) > 0) { |
996 | g_string_append(interface_names, ":")(__builtin_constant_p (":") ? __extension__ ({ const char * const __val = (":"); g_string_append_len_inline (interface_names, __val , (__val != __null) ? (gssize) strlen (((__val) + !(__val))) : (gssize) -1); }) : g_string_append_len_inline (interface_names , ":", (gssize) -1)); |
997 | } |
998 | g_string_append(interface_names, " ")(__builtin_constant_p (" ") ? __extension__ ({ const char * const __val = (" "); g_string_append_len_inline (interface_names, __val , (__val != __null) ? (gssize) strlen (((__val) + !(__val))) : (gssize) -1); }) : g_string_append_len_inline (interface_names , " ", (gssize) -1)); |
999 | |
1000 | mainApp->popStatus(WiresharkApplication::FileStatus); |
1001 | QString msg = QString("%1<live capture in progress>").arg(interface_names->str); |
1002 | QString msgtip = QString("to file: "); |
1003 | if (capture_opts->save_file) |
1004 | msgtip += capture_opts->save_file; |
1005 | mainApp->pushStatus(WiresharkApplication::FileStatus, msg, msgtip); |
1006 | g_string_free(interface_names, TRUE)(__builtin_constant_p ((!(0))) ? (((!(0))) ? (g_string_free) ( (interface_names), ((!(0)))) : g_string_free_and_steal (interface_names )) : (g_string_free) ((interface_names), ((!(0))))); |
1007 | #endif // HAVE_LIBPCAP |
1008 | } |
1009 | |
1010 | void WiresharkMainWindow::popLiveCaptureInProgress() { |
1011 | /* Pop the "<live capture in progress>" message off the status bar. */ |
1012 | main_ui_->statusBar->setFileName(capture_file_); |
1013 | } |
1014 | |
1015 | void WiresharkMainWindow::stopCapture() { |
1016 | //#ifdef HAVE_AIRPCAP |
1017 | // if (airpcap_if_active) |
1018 | // airpcap_set_toolbar_stop_capture(airpcap_if_active); |
1019 | //#endif |
1020 | |
1021 | #ifdef HAVE_LIBPCAP1 |
1022 | capture_stop(&cap_session_); |
1023 | #endif // HAVE_LIBPCAP |
1024 | |
1025 | } |
1026 | |
1027 | // Keep focus rects from showing through the welcome screen. Primarily for |
1028 | // macOS. |
1029 | void WiresharkMainWindow::mainStackChanged(int) |
1030 | { |
1031 | for (int i = 0; i < main_ui_->mainStack->count(); i++) { |
1032 | main_ui_->mainStack->widget(i)->setEnabled(i == main_ui_->mainStack->currentIndex()); |
1033 | } |
1034 | } |
1035 | |
1036 | // XXX - Copied from ui/gtk/menus.c |
1037 | |
1038 | /** |
1039 | * Add the capture filename (with an absolute path) to the "Recent Files" menu. |
1040 | */ |
1041 | // XXX - We should probably create a RecentFile class. |
1042 | void WiresharkMainWindow::updateRecentCaptures() { |
1043 | QAction *ra; |
1044 | QMenu *recentMenu = main_ui_->menuOpenRecentCaptureFile; |
1045 | QString action_cf_name; |
1046 | |
1047 | if (!recentMenu) { |
1048 | return; |
1049 | } |
1050 | recentMenu->clear(); |
1051 | |
1052 | #if 0 |
1053 | #if defined(QT_WINEXTRAS_LIB) |
1054 | QWinJumpList recent_jl(this); |
1055 | QWinJumpListCategory *recent_jlc = recent_jl.recent(); |
1056 | if (recent_jlc) { |
1057 | recent_jlc->clear(); |
1058 | recent_jlc->setVisible(true); |
1059 | } |
1060 | #endif |
1061 | #endif |
1062 | #if defined(Q_OS_MAC) |
1063 | if (!dock_menu_) { |
1064 | dock_menu_ = new QMenu(); |
1065 | dock_menu_->setAsDockMenu(); |
1066 | } |
1067 | dock_menu_->clear(); |
1068 | #endif |
1069 | |
1070 | /* Iterate through the actions in menuOpenRecentCaptureFile, |
1071 | * removing special items, a maybe duplicate entry and every item above count_max */ |
1072 | #if defined(Q_OS_MAC) |
1073 | int shortcut = Qt::Key_0; |
1074 | #endif |
1075 | foreach(recent_item_status *ri, mainApp->recentItems())for (auto _container_1075 = QtPrivate::qMakeForeachContainer( mainApp->recentItems()); _container_1075.i != _container_1075 .e; ++_container_1075.i) if (recent_item_status *ri = *_container_1075 .i; false) {} else { |
1076 | // Add the new item |
1077 | ra = new QAction(recentMenu); |
1078 | ra->setData(ri->filename); |
1079 | // XXX - Needs get_recent_item_status or equivalent |
1080 | ra->setEnabled(ri->accessible); |
1081 | recentMenu->insertAction(NULL__null, ra); |
1082 | action_cf_name = ra->data().toString(); |
1083 | #if defined(Q_OS_MAC) |
1084 | if (shortcut <= Qt::Key_9) { |
1085 | ra->setShortcut(Qt::META | (Qt::Key)shortcut); |
1086 | shortcut++; |
1087 | } |
1088 | #endif |
1089 | ra->setText(action_cf_name); |
1090 | connect(ra, &QAction::triggered, this, &WiresharkMainWindow::recentActionTriggered); |
1091 | |
1092 | /* This is slow, at least on my VM here. The added links also open Wireshark |
1093 | * in a new window. It might make more sense to add a recent item when we |
1094 | * open a capture file. */ |
1095 | #if 0 |
1096 | #if defined(QT_WINEXTRAS_LIB) |
1097 | if (recent_jlc) { |
1098 | QFileInfo fi(ri->filename); |
1099 | QWinJumpListItem *jli = recent_jlc->addLink( |
1100 | fi.fileName(), |
1101 | QApplication::applicationFilePath(), |
1102 | QStringList() << "-r" << ri->filename |
1103 | ); |
1104 | // XXX set icon |
1105 | jli->setWorkingDirectory(QDir::toNativeSeparators(QApplication::applicationDirPath())); |
1106 | } |
1107 | #endif |
1108 | #endif |
1109 | #if defined(Q_OS_MAC) |
1110 | QAction *rda = new QAction(dock_menu_); |
1111 | QFileInfo fi(ri->filename); |
1112 | rda->setText(fi.fileName()); |
1113 | dock_menu_->insertAction(NULL__null, rda); |
1114 | connect(rda, &QAction::triggered, ra, &QAction::trigger); |
1115 | #endif |
1116 | #if QT_VERSION((6<<16)|(4<<8)|(2)) < QT_VERSION_CHECK(6, 0, 0)((6<<16)|(0<<8)|(0)) |
1117 | if (recentMenu->actions().count() == static_cast<int>(prefs.gui_recent_files_count_max)) { |
1118 | #else |
1119 | if (recentMenu->actions().count() == static_cast<qsizetype>(prefs.gui_recent_files_count_max)) { |
1120 | #endif |
1121 | break; |
1122 | } |
1123 | } |
1124 | |
1125 | if (recentMenu->actions().count() > 0) { |
1126 | // Separator + "Clear" |
1127 | // XXX - Do we really need this? |
1128 | ra = new QAction(recentMenu); |
1129 | ra->setSeparator(true); |
1130 | recentMenu->insertAction(NULL__null, ra); |
1131 | |
1132 | ra = new QAction(recentMenu); |
1133 | ra->setText(tr("Clear Menu")); |
1134 | recentMenu->insertAction(NULL__null, ra); |
1135 | connect(ra, &QAction::triggered, mainApp, &MainApplication::clearRecentCaptures); |
1136 | } else { |
1137 | if (main_ui_->actionDummyNoFilesFound) { |
1138 | recentMenu->addAction(main_ui_->actionDummyNoFilesFound); |
1139 | } |
1140 | } |
1141 | } |
1142 | |
1143 | void WiresharkMainWindow::recentActionTriggered() { |
1144 | QAction *ra = qobject_cast<QAction*>(sender()); |
1145 | |
1146 | if (ra) { |
1147 | QString cfPath = ra->data().toString(); |
1148 | openCaptureFile(cfPath); |
1149 | } |
1150 | } |
1151 | |
1152 | QString WiresharkMainWindow::commentToMenuText(QString text, int max_len) |
1153 | { |
1154 | text = text.trimmed().replace(QRegularExpression("(\\r?\\n|\\r\\n?)+"), " "); |
1155 | if (text.size() > 0) { |
1156 | if (text.size() > max_len) { |
1157 | text.truncate(max_len); |
1158 | text += "…"; |
1159 | } |
1160 | } |
1161 | else { |
1162 | text = tr("(empty comment)", "placeholder for empty comment"); |
1163 | } |
1164 | return text; |
1165 | } |
1166 | |
1167 | void WiresharkMainWindow::setEditCommentsMenu() |
1168 | { |
1169 | main_ui_->menuPacketComment->clear(); |
1170 | QAction *action = main_ui_->menuPacketComment->addAction(tr("Add New Comment…")); |
1171 | connect(action, &QAction::triggered, this, &WiresharkMainWindow::addPacketComment); |
1172 | action->setShortcut(QKeySequence(Qt::CTRL | Qt::ALT | Qt::Key_C)); |
1173 | if (selectedRows().count() == 1) { |
1174 | const int thisRow = selectedRows().first(); |
1175 | frame_data * current_frame = frameDataForRow(thisRow); |
1176 | wtap_block_t pkt_block = cf_get_packet_block(capture_file_.capFile(), current_frame); |
1177 | unsigned nComments = wtap_block_count_option(pkt_block, OPT_COMMENT1); |
1178 | if (nComments > 0) { |
1179 | main_ui_->menuPacketComment->addSeparator(); |
1180 | for (unsigned i = 0; i < nComments; i++) { |
1181 | QString comment = packet_list_->getPacketComment(i); |
1182 | comment = this->commentToMenuText(comment); |
1183 | action = main_ui_->menuPacketComment->addAction(tr("Edit \"%1\"", "edit packet comment").arg(comment)); |
1184 | connect(action, &QAction::triggered, this, &WiresharkMainWindow::editPacketComment); |
1185 | action->setData(i); |
1186 | } |
1187 | |
1188 | main_ui_->menuPacketComment->addSeparator(); |
1189 | for (unsigned i = 0; i < nComments; i++) { |
1190 | QString comment = packet_list_->getPacketComment(i); |
1191 | comment = this->commentToMenuText(comment); |
1192 | action = main_ui_->menuPacketComment->addAction(tr("Delete \"%1\"", "delete packet comment").arg(comment)); |
1193 | connect(action, &QAction::triggered, this, &WiresharkMainWindow::deletePacketComment); |
1194 | action->setData(i); |
1195 | } |
1196 | main_ui_->menuPacketComment->addSeparator(); |
1197 | action = main_ui_->menuPacketComment->addAction(tr("Delete packet comments")); |
1198 | connect(action, &QAction::triggered, this, &WiresharkMainWindow::deleteCommentsFromPackets); |
1199 | } |
1200 | wtap_block_unref(pkt_block); |
1201 | } |
1202 | if (selectedRows().count() > 1) { |
1203 | main_ui_->menuPacketComment->addSeparator(); |
1204 | action = main_ui_->menuPacketComment->addAction(tr("Delete comments from %n packet(s)", nullptr, static_cast<int>(selectedRows().count()))); |
1205 | connect(action, &QAction::triggered, this, &WiresharkMainWindow::deleteCommentsFromPackets); |
1206 | } |
1207 | } |
1208 | |
1209 | void WiresharkMainWindow::setMenusForSelectedPacket() |
1210 | { |
1211 | bool is_ip = false, is_tcp = false, is_udp = false, is_sctp = false, is_tls = false, is_rtp = false, is_lte_rlc = false, |
1212 | is_quic = false, is_exported_pdu = false; |
1213 | |
1214 | /* Making the menu context-sensitive allows for easier selection of the |
1215 | desired item and has the added benefit, with large captures, of |
1216 | avoiding needless looping through huge lists for marked, ignored, |
1217 | or time-referenced packets. */ |
1218 | |
1219 | /* We have one or more items in the packet list */ |
1220 | bool have_frames = false; |
1221 | /* A frame is selected */ |
1222 | bool frame_selected = false; |
1223 | bool multi_selection = false; |
1224 | /* A visible packet comes after this one in the selection history */ |
1225 | bool next_selection_history = false; |
1226 | /* A visible packet comes before this one in the selection history */ |
1227 | bool previous_selection_history = false; |
1228 | /* We have marked frames. (XXX - why check frame_selected?) */ |
1229 | bool have_marked = false; |
1230 | /* We have a marked frame other than the current frame (i.e., |
1231 | we have at least one marked frame, and either there's more |
1232 | than one marked frame or the current frame isn't marked). */ |
1233 | bool another_is_marked = false; |
1234 | /* One or more frames are hidden by a display filter */ |
1235 | bool have_filtered = false; |
1236 | /* One or more frames have been ignored */ |
1237 | bool have_ignored = false; |
1238 | bool have_time_ref = false; |
1239 | /* We have a time reference frame other than the current frame (i.e., |
1240 | we have at least one time reference frame, and either there's more |
1241 | than one time reference frame or the current frame isn't a |
1242 | time reference frame). (XXX - why check frame_selected?) */ |
1243 | bool another_is_time_ref = false; |
1244 | |
1245 | QList<QAction *> cc_actions = QList<QAction *>() |
1246 | << main_ui_->actionViewColorizeConversation1 << main_ui_->actionViewColorizeConversation2 |
1247 | << main_ui_->actionViewColorizeConversation3 << main_ui_->actionViewColorizeConversation4 |
1248 | << main_ui_->actionViewColorizeConversation5 << main_ui_->actionViewColorizeConversation6 |
1249 | << main_ui_->actionViewColorizeConversation7 << main_ui_->actionViewColorizeConversation8 |
1250 | << main_ui_->actionViewColorizeConversation9 << main_ui_->actionViewColorizeConversation10; |
1251 | |
1252 | if (capture_file_.capFile()) { |
| 5 | | Assuming the condition is true | |
|
| |
1253 | QList<int> rows = selectedRows(); |
1254 | frame_data * current_frame = 0; |
| 7 | | 'current_frame' initialized to a null pointer value | |
|
1255 | if (rows.count() > 0) |
| 8 | | Assuming the condition is false | |
|
| |
1256 | current_frame = frameDataForRow(rows.at(0)); |
1257 | |
1258 | frame_selected = rows.count() == 1; |
| 10 | | Assuming the condition is true | |
|
1259 | if (packet_list_->multiSelectActive()) |
| 11 | | Assuming the condition is false | |
|
| |
1260 | { |
1261 | frame_selected = false; |
1262 | multi_selection = true; |
1263 | } |
1264 | next_selection_history = packet_list_->haveNextHistory(); |
1265 | previous_selection_history = packet_list_->havePreviousHistory(); |
1266 | have_frames = capture_file_.capFile()->count > 0; |
| 13 | | Assuming field 'count' is <= 0 | |
|
1267 | have_marked = capture_file_.capFile()->marked_count > 0; |
| 14 | | Assuming field 'marked_count' is <= 0 | |
|
1268 | another_is_marked = have_marked14.1 | 'have_marked' is false |
14.1 | 'have_marked' is false | && rows.count() <= 1 && |
1269 | !(capture_file_.capFile()->marked_count == 1 && frame_selected && current_frame->marked); |
1270 | have_filtered = capture_file_.capFile()->displayed_count > 0 && capture_file_.capFile()->displayed_count != capture_file_.capFile()->count; |
| 15 | | Assuming field 'displayed_count' is <= 0 | |
|
1271 | have_ignored = capture_file_.capFile()->ignored_count > 0; |
| 16 | | Assuming field 'ignored_count' is <= 0 | |
|
1272 | have_time_ref = capture_file_.capFile()->ref_time_count > 0; |
| 17 | | Assuming field 'ref_time_count' is > 0 | |
|
1273 | another_is_time_ref = have_time_ref17.1 | 'have_time_ref' is true |
17.1 | 'have_time_ref' is true | && rows.count() <= 1 && |
| 18 | | Assuming the condition is true | |
|
1274 | !(capture_file_.capFile()->ref_time_count == 1 && frame_selected19.1 | 'frame_selected' is true |
19.1 | 'frame_selected' is true | && current_frame->ref_time); |
| 19 | | Assuming field 'ref_time_count' is equal to 1 | |
|
| 20 | | Access to field 'ref_time' results in a dereference of a null pointer (loaded from variable 'current_frame') |
|
1275 | |
1276 | if (capture_file_.capFile()->edt && ! multi_selection && frame_selected) |
1277 | { |
1278 | proto_get_frame_protocols(capture_file_.capFile()->edt->pi.layers, |
1279 | &is_ip, &is_tcp, &is_udp, &is_sctp, |
1280 | &is_tls, &is_rtp, &is_lte_rlc); |
1281 | /* TODO: to follow a QUIC stream we need a *decrypted* QUIC connection, i.e. checking for "quic" in the protocol stack is not enough */ |
1282 | is_quic = proto_is_frame_protocol(capture_file_.capFile()->edt->pi.layers, "quic"); |
1283 | is_exported_pdu = proto_is_frame_protocol(capture_file_.capFile()->edt->pi.layers, "exported_pdu"); |
1284 | /* For Exported PDU there is a tag inserting IP addresses into the SRC and DST columns */ |
1285 | if (is_exported_pdu && |
1286 | (capture_file_.capFile()->edt->pi.net_src.type == AT_IPv4 || capture_file_.capFile()->edt->pi.net_src.type == AT_IPv6) && |
1287 | (capture_file_.capFile()->edt->pi.net_dst.type == AT_IPv4 || capture_file_.capFile()->edt->pi.net_dst.type == AT_IPv6)) { |
1288 | is_ip = true; |
1289 | } |
1290 | foreach (FollowStreamAction *follow_action, main_ui_->menuFollow->findChildren<FollowStreamAction *>())for (auto _container_1290 = QtPrivate::qMakeForeachContainer( main_ui_->menuFollow->findChildren<FollowStreamAction *>()); _container_1290.i != _container_1290.e; ++_container_1290 .i) if (FollowStreamAction *follow_action = *_container_1290. i; false) {} else { |
1291 | /* QUIC has TLS handshakes; don't enabled Follow TLS Stream if |
1292 | * there's QUIC. |
1293 | */ |
1294 | bool is_frame = proto_is_frame_protocol(capture_file_.capFile()->edt->pi.layers, follow_action->filterName()); |
1295 | if (g_strcmp0(follow_action->filterName(), "tls") == 0) { |
1296 | follow_action->setEnabled(is_frame && !is_quic); |
1297 | } else { |
1298 | follow_action->setEnabled(is_frame); |
1299 | } |
1300 | } |
1301 | } else { |
1302 | foreach (FollowStreamAction *follow_action, main_ui_->menuFollow->findChildren<FollowStreamAction *>())for (auto _container_1302 = QtPrivate::qMakeForeachContainer( main_ui_->menuFollow->findChildren<FollowStreamAction *>()); _container_1302.i != _container_1302.e; ++_container_1302 .i) if (FollowStreamAction *follow_action = *_container_1302. i; false) {} else { |
1303 | follow_action->setEnabled(false); |
1304 | } |
1305 | } |
1306 | } |
1307 | |
1308 | main_ui_->actionCopyListAsText->setEnabled(selectedRows().count() > 0); |
1309 | main_ui_->actionCopyListAsCSV->setEnabled(selectedRows().count() > 0); |
1310 | main_ui_->actionCopyListAsYAML->setEnabled(selectedRows().count() > 0); |
1311 | |
1312 | main_ui_->actionEditMarkSelected->setEnabled(frame_selected || multi_selection); |
1313 | main_ui_->actionEditMarkAllDisplayed->setEnabled(have_frames); |
1314 | /* Unlike un-ignore, do not allow unmark of all frames when no frames are displayed */ |
1315 | main_ui_->actionEditUnmarkAllDisplayed->setEnabled(have_marked); |
1316 | main_ui_->actionEditNextMark->setEnabled(another_is_marked); |
1317 | main_ui_->actionEditPreviousMark->setEnabled(another_is_marked); |
1318 | |
1319 | GArray * linkTypes = Q_NULLPTRnullptr; |
1320 | if (capture_file_.capFile() && capture_file_.capFile()->linktypes) |
1321 | linkTypes = capture_file_.capFile()->linktypes; |
1322 | |
1323 | bool enableEditComments = linkTypes && wtap_dump_can_write(capture_file_.capFile()->linktypes, WTAP_COMMENT_PER_PACKET0x00000004); |
1324 | main_ui_->menuPacketComment->setEnabled(enableEditComments && selectedRows().count() > 0); |
1325 | main_ui_->actionDeleteAllPacketComments->setEnabled(enableEditComments); |
1326 | |
1327 | main_ui_->actionEditIgnoreSelected->setEnabled(frame_selected || multi_selection); |
1328 | main_ui_->actionEditIgnoreAllDisplayed->setEnabled(have_filtered); |
1329 | /* Allow un-ignore of all frames even with no frames currently displayed */ |
1330 | main_ui_->actionEditUnignoreAllDisplayed->setEnabled(have_ignored); |
1331 | |
1332 | // XXX: Should we allow frames that don't have a time stamp to be |
1333 | // set as time references? "Time" references are also used to reset |
1334 | // the "Cumulative Bytes", so it's not entirely useless. |
1335 | main_ui_->actionEditSetTimeReference->setEnabled(frame_selected); |
1336 | main_ui_->actionEditUnsetAllTimeReferences->setEnabled(have_time_ref); |
1337 | main_ui_->actionEditNextTimeReference->setEnabled(another_is_time_ref); |
1338 | main_ui_->actionEditPreviousTimeReference->setEnabled(another_is_time_ref); |
1339 | main_ui_->actionEditTimeShift->setEnabled(have_frames); |
1340 | |
1341 | main_ui_->actionGoGoToLinkedPacket->setEnabled(false); |
1342 | main_ui_->actionGoNextHistoryPacket->setEnabled(next_selection_history); |
1343 | main_ui_->actionGoPreviousHistoryPacket->setEnabled(previous_selection_history); |
1344 | |
1345 | foreach(QAction *cc_action, cc_actions)for (auto _container_1345 = QtPrivate::qMakeForeachContainer( cc_actions); _container_1345.i != _container_1345.e; ++_container_1345 .i) if (QAction *cc_action = *_container_1345.i; false) {} else { |
1346 | cc_action->setEnabled(frame_selected); |
1347 | } |
1348 | main_ui_->actionViewColorizeNewColoringRule->setEnabled(frame_selected); |
1349 | |
1350 | main_ui_->actionViewColorizeResetColorization->setEnabled(tmp_color_filters_used()); |
1351 | |
1352 | main_ui_->actionViewShowPacketInNewWindow->setEnabled(frame_selected); |
1353 | main_ui_->actionViewEditResolvedName->setEnabled(frame_selected && is_ip); |
1354 | |
1355 | emit packetInfoChanged(capture_file_.packetInfo()); |
1356 | |
1357 | // set_menu_sensitivity(ui_manager_main_menubar, "/Menubar/ViewMenu/NameResolution/ResolveName", |
1358 | // frame_selected && (gbl_resolv_flags.mac_name || gbl_resolv_flags.network_name || |
1359 | // gbl_resolv_flags.transport_name)); |
1360 | |
1361 | main_ui_->actionToolsFirewallAclRules->setEnabled(frame_selected); |
1362 | |
1363 | main_ui_->actionStatisticsTcpStreamRoundTripTime->setEnabled(is_tcp); |
1364 | main_ui_->actionStatisticsTcpStreamStevens->setEnabled(is_tcp); |
1365 | main_ui_->actionStatisticsTcpStreamTcptrace->setEnabled(is_tcp); |
1366 | main_ui_->actionStatisticsTcpStreamThroughput->setEnabled(is_tcp); |
1367 | main_ui_->actionStatisticsTcpStreamWindowScaling->setEnabled(is_tcp); |
1368 | |
1369 | main_ui_->actionSCTPAnalyseThisAssociation->setEnabled(is_sctp); |
1370 | main_ui_->actionSCTPShowAllAssociations->setEnabled(is_sctp); |
1371 | main_ui_->actionSCTPFilterThisAssociation->setEnabled(is_sctp); |
1372 | main_ui_->actionTelephonyRtpStreamAnalysis->setEnabled(is_rtp); |
1373 | main_ui_->actionTelephonyRtpPlayer->setEnabled(is_rtp); |
1374 | main_ui_->actionTelephonyLteRlcGraph->setEnabled(is_lte_rlc); |
1375 | } |
1376 | |
1377 | void WiresharkMainWindow::setMenusForSelectedTreeRow(FieldInformation *finfo) { |
1378 | |
1379 | bool can_match_selected = false; |
1380 | bool is_framenum = false; |
1381 | bool have_subtree = false; |
1382 | bool can_open_url = false; |
1383 | bool have_packet_bytes = false; |
1384 | QByteArray field_filter; |
1385 | int field_id = -1; |
1386 | |
1387 | field_info * fi = 0; |
1388 | if (finfo) |
1389 | fi = finfo->fieldInfo(); |
1390 | |
1391 | if (capture_file_.capFile()) { |
1392 | capture_file_.capFile()->finfo_selected = fi; |
1393 | |
1394 | if (fi && fi->tree_type != -1) { |
1395 | have_subtree = true; |
1396 | } |
1397 | |
1398 | if (fi && fi->ds_tvb && (fi->length > 0)) { |
1399 | have_packet_bytes = true; |
1400 | } |
1401 | |
1402 | if (!(capture_file_.capFile()->search_in_progress && (capture_file_.capFile()->hex || (capture_file_.capFile()->string && capture_file_.capFile()->packet_data)))) { |
1403 | // If we're not in the middle of a packet bytes search, then set |
1404 | // search_pos and search_len so that we can start a new search |
1405 | // from this point. (If we are, then we already set it.) |
1406 | if (fi && capture_file_.capFile()->edt && (fi->ds_tvb == capture_file_.capFile()->edt->tvb)) { |
1407 | // We can only do a Packet Bytes search in the main bytes from |
1408 | // the frame, not from any secondary data sources. (XXX: This |
1409 | // might be surprising to users, though.) |
1410 | capture_file_.capFile()->search_pos = (uint32_t)(finfo->position().start + finfo->position().length - 1); |
1411 | capture_file_.capFile()->search_len = (uint32_t)finfo->position().length; |
1412 | } else { |
1413 | capture_file_.capFile()->search_pos = 0; |
1414 | capture_file_.capFile()->search_len = 0; |
1415 | } |
1416 | } |
1417 | } |
1418 | |
1419 | if (capture_file_.capFile() != NULL__null && fi != NULL__null) { |
1420 | const header_field_info *hfinfo = fi->hfinfo; |
1421 | int linked_frame = -1; |
1422 | |
1423 | can_match_selected = proto_can_match_selected(capture_file_.capFile()->finfo_selected, capture_file_.capFile()->edt); |
1424 | if (hfinfo && hfinfo->type == FT_FRAMENUM) { |
1425 | is_framenum = true; |
1426 | linked_frame = fvalue_get_uinteger(fi->value); |
1427 | } |
1428 | |
1429 | char *tmp_field = proto_construct_match_selected_string(fi, capture_file_.capFile()->edt); |
1430 | field_filter = tmp_field; |
1431 | wmem_free(NULL__null, tmp_field); |
1432 | emit fieldFilterChanged(field_filter); |
1433 | |
1434 | field_id = fi->hfinfo->id; |
1435 | /* if the selected field isn't a protocol, get its parent */ |
1436 | if (!proto_registrar_is_protocol(field_id)) { |
1437 | field_id = proto_registrar_get_parent(fi->hfinfo->id); |
1438 | } |
1439 | |
1440 | if (field_id >= 0) { |
1441 | can_open_url = true; |
1442 | main_ui_->actionContextWikiProtocolPage->setData(field_id); |
1443 | main_ui_->actionContextFilterFieldReference->setData(field_id); |
1444 | } else { |
1445 | main_ui_->actionContextWikiProtocolPage->setData(QVariant()); |
1446 | main_ui_->actionContextFilterFieldReference->setData(QVariant()); |
1447 | } |
1448 | |
1449 | if (linked_frame > 0) { |
1450 | main_ui_->actionGoGoToLinkedPacket->setData(linked_frame); |
1451 | } else { |
1452 | main_ui_->actionGoGoToLinkedPacket->setData(QVariant()); |
1453 | } |
1454 | } |
1455 | |
1456 | // Always enable / disable the following items. |
1457 | main_ui_->actionCopyAllVisibleItems->setEnabled(capture_file_.capFile() != NULL__null && ! packet_list_->multiSelectActive()); |
1458 | main_ui_->actionCopyAllVisibleSelectedTreeItems->setEnabled(can_match_selected); |
1459 | main_ui_->actionEditCopyDescription->setEnabled(can_match_selected); |
1460 | main_ui_->actionEditCopyFieldName->setEnabled(can_match_selected); |
1461 | main_ui_->actionEditCopyValue->setEnabled(can_match_selected); |
1462 | main_ui_->actionEditCopyAsFilter->setEnabled(can_match_selected); |
1463 | |
1464 | main_ui_->actionAnalyzeShowPacketBytes->setEnabled(have_packet_bytes); |
1465 | main_ui_->actionFileExportPacketBytes->setEnabled(have_packet_bytes); |
1466 | |
1467 | main_ui_->actionViewExpandSubtrees->setEnabled(have_subtree); |
1468 | main_ui_->actionViewCollapseSubtrees->setEnabled(have_subtree); |
1469 | |
1470 | main_ui_->actionGoGoToLinkedPacket->setEnabled(is_framenum); |
1471 | |
1472 | main_ui_->actionAnalyzeApplyAsColumn->setEnabled(can_match_selected); |
1473 | |
1474 | main_ui_->actionContextShowLinkedPacketInNewWindow->setEnabled(is_framenum); |
1475 | |
1476 | main_ui_->actionContextWikiProtocolPage->setEnabled(can_open_url); |
1477 | main_ui_->actionContextFilterFieldReference->setEnabled(can_open_url); |
1478 | |
1479 | |
1480 | // Only enable / disable the following items if we have focus so that we |
1481 | // don't clobber anything we may have set in setMenusForSelectedPacket. |
1482 | if (!proto_tree_ || !proto_tree_->hasFocus()) return; |
1483 | |
1484 | emit packetInfoChanged(capture_file_.packetInfo()); |
1485 | |
1486 | // set_menu_sensitivity(ui_manager_tree_view_menu, "/TreeViewPopup/ResolveName", |
1487 | // frame_selected && (gbl_resolv_flags.mac_name || gbl_resolv_flags.network_name || |
1488 | // gbl_resolv_flags.transport_name)); |
1489 | |
1490 | } |
1491 | |
1492 | void WiresharkMainWindow::interfaceSelectionChanged() |
1493 | { |
1494 | #ifdef HAVE_LIBPCAP1 |
1495 | // XXX This doesn't disable the toolbar button when using |
1496 | // QtMacExtras. |
1497 | if (global_capture_opts.num_selected > 0 && capture_filter_valid_) { |
1498 | main_ui_->actionCaptureStart->setEnabled(true); |
1499 | } else { |
1500 | main_ui_->actionCaptureStart->setEnabled(false); |
1501 | } |
1502 | #endif // HAVE_LIBPCAP |
1503 | } |
1504 | |
1505 | void WiresharkMainWindow::captureFilterSyntaxChanged(bool valid) |
1506 | { |
1507 | capture_filter_valid_ = valid; |
1508 | interfaceSelectionChanged(); |
1509 | } |
1510 | |
1511 | void WiresharkMainWindow::startInterfaceCapture(bool valid, const QString capture_filter) |
1512 | { |
1513 | capture_filter_valid_ = valid; |
1514 | welcome_page_->setCaptureFilter(capture_filter); |
1515 | QString before_what(tr(" before starting a new capture")); |
1516 | if (testCaptureFileClose(before_what)) { |
1517 | // The interface tree will update the selected interfaces via its timer |
1518 | // so no need to do anything here. |
1519 | startCapture(QStringList()); |
1520 | } |
1521 | } |
1522 | |
1523 | void WiresharkMainWindow::applyGlobalCommandLineOptions() |
1524 | { |
1525 | if (global_dissect_options.time_format != TS_NOT_SET) { |
1526 | foreach(QAction* tda, td_actions.keys())for (auto _container_1526 = QtPrivate::qMakeForeachContainer( td_actions.keys()); _container_1526.i != _container_1526.e; ++ _container_1526.i) if (QAction* tda = *_container_1526.i; false ) {} else { |
1527 | if (global_dissect_options.time_format == td_actions[tda]) { |
1528 | tda->setChecked(true); |
1529 | // XXX - this means that if the user sets the |
1530 | // time stamp format with the -t flag, that |
1531 | // setting will persist and will be used as |
1532 | // the default the next time Wireshark is run. |
1533 | recent.gui_time_format = global_dissect_options.time_format; |
1534 | timestamp_set_type(global_dissect_options.time_format); |
1535 | break; |
1536 | } |
1537 | } |
1538 | } |
1539 | if (global_dissect_options.time_precision != TS_PREC_NOT_SET) { |
1540 | foreach(QAction* tpa, tp_actions.keys())for (auto _container_1540 = QtPrivate::qMakeForeachContainer( tp_actions.keys()); _container_1540.i != _container_1540.e; ++ _container_1540.i) if (QAction* tpa = *_container_1540.i; false ) {} else { |
1541 | if (global_dissect_options.time_precision == tp_actions[tpa]) { |
1542 | tpa->setChecked(true); |
1543 | // XXX - this means that if the user sets the |
1544 | // time stamp precision with the -t flag, that |
1545 | // setting will persist and will be used as |
1546 | // the default the next time Wireshark is run. |
1547 | recent.gui_time_precision = global_dissect_options.time_precision; |
1548 | timestamp_set_precision(global_dissect_options.time_precision); |
1549 | break; |
1550 | } |
1551 | } |
1552 | } |
1553 | if (global_commandline_info.full_screen) { |
1554 | this->showFullScreen(); |
1555 | } |
1556 | } |
1557 | |
1558 | void WiresharkMainWindow::redissectPackets() |
1559 | { |
1560 | if (capture_file_.capFile()) { |
1561 | cf_redissect_packets(capture_file_.capFile()); |
1562 | main_ui_->statusBar->expertUpdate(); |
1563 | } |
1564 | |
1565 | proto_free_deregistered_fields(); |
1566 | } |
1567 | |
1568 | void WiresharkMainWindow::checkDisplayFilter() |
1569 | { |
1570 | if (!df_combo_box_->checkDisplayFilter()) { |
1571 | g_free(CaptureFile::globalCapFile()->dfilter); |
1572 | CaptureFile::globalCapFile()->dfilter = NULL__null; |
1573 | } |
1574 | } |
1575 | |
1576 | void WiresharkMainWindow::fieldsChanged() |
1577 | { |
1578 | char *err_msg = NULL__null; |
1579 | if (!color_filters_reload(&err_msg, color_filter_add_cb)) { |
1580 | simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK0x01, "%s", err_msg); |
1581 | g_free(err_msg); |
1582 | } |
1583 | tap_listeners_dfilter_recompile(); |
1584 | |
1585 | emit checkDisplayFilter(); |
1586 | |
1587 | if (have_custom_cols(&CaptureFile::globalCapFile()->cinfo)) { |
1588 | // Recreate packet list columns according to new/changed/deleted fields |
1589 | packet_list_->fieldsChanged(CaptureFile::globalCapFile()); |
1590 | } |
1591 | |
1592 | emit reloadFields(); |
1593 | } |
1594 | |
1595 | void WiresharkMainWindow::reloadLuaPlugins() |
1596 | { |
1597 | #ifdef HAVE_LUA1 |
1598 | if (mainApp->isReloadingLua()) |
1599 | return; |
1600 | |
1601 | bool uses_lua_filehandler = false; |
1602 | |
1603 | if (capture_file_.capFile()) { |
1604 | // Check if the current capture file is opened with a Lua FileHandler |
1605 | capture_file *cf = capture_file_.capFile(); |
1606 | uses_lua_filehandler = wtap_uses_lua_filehandler(cf->provider.wth); |
1607 | |
1608 | if (uses_lua_filehandler && cf->unsaved_changes) { |
1609 | // Prompt to save the file before reloading, in case the FileHandler has changed |
1610 | QString before_what(tr(" before reloading Lua plugins")); |
1611 | if (!testCaptureFileClose(before_what, Reload)) { |
1612 | return; |
1613 | } |
1614 | } |
1615 | } |
1616 | |
1617 | mainApp->setReloadingLua(true); |
1618 | |
1619 | wslua_reload_plugins(NULL__null, NULL__null); |
1620 | this->clearAddedPacketMenus(); |
1621 | funnel_statistics_reload_menus(); |
1622 | reloadDynamicMenus(); |
1623 | closePacketDialogs(); |
1624 | |
1625 | // Preferences may have been deleted so close all widgets using prefs |
1626 | main_ui_->preferenceEditorFrame->animatedHide(); |
1627 | |
1628 | mainApp->readConfigurationFiles(true); |
1629 | commandline_options_reapply(); |
1630 | |
1631 | fieldsChanged(); |
1632 | prefs_apply_all(); |
1633 | |
1634 | if (uses_lua_filehandler) { |
1635 | // Reload the file in case the FileHandler has changed |
1636 | if (cf_reload(capture_file_.capFile()) != CF_OK) { |
1637 | cf_close(capture_file_.capFile()); |
1638 | } |
1639 | proto_free_deregistered_fields(); |
1640 | } else { |
1641 | redissectPackets(); |
1642 | } |
1643 | |
1644 | mainApp->setReloadingLua(false); |
1645 | SimpleDialog::displayQueuedMessages(); |
1646 | #endif |
1647 | } |
1648 | |
1649 | void WiresharkMainWindow::showAccordionFrame(AccordionFrame *show_frame, bool toggle) |
1650 | { |
1651 | QList<AccordionFrame *>frame_list = QList<AccordionFrame *>() |
1652 | << main_ui_->goToFrame << main_ui_->searchFrame |
1653 | << main_ui_->addressEditorFrame << main_ui_->columnEditorFrame |
1654 | << main_ui_->preferenceEditorFrame << main_ui_->filterExpressionFrame; |
1655 | |
1656 | frame_list.removeAll(show_frame); |
1657 | foreach(AccordionFrame *af, frame_list)for (auto _container_1657 = QtPrivate::qMakeForeachContainer( frame_list); _container_1657.i != _container_1657.e; ++_container_1657 .i) if (AccordionFrame *af = *_container_1657.i; false) {} else af->animatedHide(); |
1658 | |
1659 | if (toggle) { |
1660 | if (show_frame->isVisible()) { |
1661 | show_frame->animatedHide(); |
1662 | return; |
1663 | } |
1664 | } |
1665 | show_frame->animatedShow(); |
1666 | } |
1667 | |
1668 | void WiresharkMainWindow::showColumnEditor(int column) |
1669 | { |
1670 | setPreviousFocus(); |
1671 | main_ui_->columnEditorFrame->editColumn(column); |
1672 | showAccordionFrame(main_ui_->columnEditorFrame); |
1673 | } |
1674 | |
1675 | void WiresharkMainWindow::showPreferenceEditor() |
1676 | { |
1677 | showAccordionFrame(main_ui_->preferenceEditorFrame); |
1678 | } |
1679 | |
1680 | void WiresharkMainWindow::initViewColorizeMenu() |
1681 | { |
1682 | QList<QAction *> cc_actions = QList<QAction *>() |
1683 | << main_ui_->actionViewColorizeConversation1 << main_ui_->actionViewColorizeConversation2 |
1684 | << main_ui_->actionViewColorizeConversation3 << main_ui_->actionViewColorizeConversation4 |
1685 | << main_ui_->actionViewColorizeConversation5 << main_ui_->actionViewColorizeConversation6 |
1686 | << main_ui_->actionViewColorizeConversation7 << main_ui_->actionViewColorizeConversation8 |
1687 | << main_ui_->actionViewColorizeConversation9 << main_ui_->actionViewColorizeConversation10; |
1688 | |
1689 | uint8_t color_num = 1; |
1690 | |
1691 | foreach(QAction *cc_action, cc_actions)for (auto _container_1691 = QtPrivate::qMakeForeachContainer( cc_actions); _container_1691.i != _container_1691.e; ++_container_1691 .i) if (QAction *cc_action = *_container_1691.i; false) {} else { |
1692 | cc_action->setData(color_num); |
1693 | connect(cc_action, &QAction::triggered, this, &WiresharkMainWindow::colorizeConversation); |
1694 | |
1695 | const color_filter_t *colorf = color_filters_tmp_color(color_num); |
1696 | if (colorf) { |
1697 | QColor bg = ColorUtils::fromColorT(colorf->bg_color); |
1698 | QColor fg = ColorUtils::fromColorT(colorf->fg_color); |
1699 | cc_action->setIcon(StockIcon::colorIcon(bg.rgb(), fg.rgb(), QString::number(color_num))); |
1700 | } |
1701 | color_num++; |
1702 | } |
1703 | |
1704 | #ifdef Q_OS_MAC |
1705 | // Spotlight uses Cmd+Space |
1706 | main_ui_->actionViewColorizeResetColorization->setShortcut(QKeySequence("Meta+Space")); |
1707 | #endif |
1708 | } |
1709 | |
1710 | void WiresharkMainWindow::addStatsPluginsToMenu() { |
1711 | GList *cfg_list = stats_tree_get_cfg_list(); |
1712 | QAction *stats_tree_action; |
1713 | QMenu *parent_menu; |
1714 | bool first_item = true; |
1715 | |
1716 | for (GList *iter = g_list_first(cfg_list); iter; iter = gxx_list_next(iter)((iter) ? ((reinterpret_cast<GList *>(iter))->next) : nullptr)) { |
1717 | stats_tree_cfg *cfg = gxx_list_data(stats_tree_cfg *, iter)((iter) ? ((reinterpret_cast<stats_tree_cfg *>(iter-> data))) : nullptr); |
1718 | if (!menu_groups_.contains(cfg->stat_group)) { |
1719 | continue; |
1720 | } |
1721 | if (cfg->plugin) { |
1722 | if (first_item) { |
1723 | main_ui_->menuStatistics->addSeparator(); |
1724 | first_item = false; |
1725 | } |
1726 | |
1727 | parent_menu = main_ui_->menuStatistics; |
1728 | // gtk/main_menubar.c compresses double slashes, hence SkipEmptyParts |
1729 | #if QT_VERSION((6<<16)|(4<<8)|(2)) >= QT_VERSION_CHECK(5, 15, 0)((5<<16)|(15<<8)|(0)) |
1730 | QStringList cfg_name_parts = QString(cfg->path).split(STATS_TREE_MENU_SEPARATOR"//", Qt::SkipEmptyParts); |
1731 | #else |
1732 | QStringList cfg_name_parts = QString(cfg->path).split(STATS_TREE_MENU_SEPARATOR"//", QString::SkipEmptyParts); |
1733 | #endif |
1734 | if (cfg_name_parts.isEmpty()) continue; |
1735 | |
1736 | QString stat_name = cfg_name_parts.takeLast().trimmed(); |
1737 | if (!cfg_name_parts.isEmpty()) { |
1738 | parent_menu = findOrAddMenu(parent_menu, cfg_name_parts); |
1739 | } |
1740 | |
1741 | stats_tree_action = new QAction(stat_name, this); |
1742 | stats_tree_action->setData(QString::fromUtf8(cfg->abbr)); |
1743 | parent_menu->addAction(stats_tree_action); |
1744 | connect(stats_tree_action, &QAction::triggered, this, [this]() { |
1745 | QAction* action = qobject_cast<QAction*>(sender()); |
1746 | if (action) { |
1747 | openStatisticsTreeDialog(action->data().toString().toUtf8()); |
1748 | } |
1749 | }); |
1750 | } |
1751 | } |
1752 | g_list_free(cfg_list); |
1753 | } |
1754 | |
1755 | void WiresharkMainWindow::setFeaturesEnabled(bool enabled) |
1756 | { |
1757 | main_ui_->menuBar->setEnabled(enabled); |
1758 | main_ui_->mainToolBar->setEnabled(enabled); |
1759 | main_ui_->displayFilterToolBar->setEnabled(enabled); |
1760 | if (enabled) |
1761 | { |
1762 | main_ui_->statusBar->clearMessage(); |
1763 | #ifdef HAVE_LIBPCAP1 |
1764 | main_ui_->actionGoAutoScroll->setChecked(recent.capture_auto_scroll); |
1765 | #endif |
1766 | } |
1767 | else |
1768 | { |
1769 | main_ui_->statusBar->showMessage(tr("Please wait while Wireshark is initializing…")); |
1770 | } |
1771 | } |
1772 | |
1773 | // Display Filter Toolbar |
1774 | |
1775 | void WiresharkMainWindow::on_actionNewDisplayFilterExpression_triggered() |
1776 | { |
1777 | main_ui_->filterExpressionFrame->addExpression(df_combo_box_->lineEdit()->text()); |
1778 | } |
1779 | |
1780 | void WiresharkMainWindow::onFilterSelected(QString filterText, bool prepare) |
1781 | { |
1782 | if (filterText.length() <= 0) |
1783 | return; |
1784 | |
1785 | df_combo_box_->setDisplayFilter(filterText); |
1786 | // Holding down the Shift key will only prepare filter. |
1787 | if (!prepare) |
1788 | df_combo_box_->applyDisplayFilter(); |
1789 | } |
1790 | |
1791 | void WiresharkMainWindow::onFilterPreferences() |
1792 | { |
1793 | emit showPreferencesDialog(PrefsModel::typeToString(PrefsModel::FilterButtons)); |
1794 | } |
1795 | |
1796 | void WiresharkMainWindow::onFilterEdit(int uatIndex) |
1797 | { |
1798 | main_ui_->filterExpressionFrame->editExpression(uatIndex); |
1799 | } |
1800 | |
1801 | void WiresharkMainWindow::openStatCommandDialog(const QString &menu_path, const char *arg, void *userdata) |
1802 | { |
1803 | QString slot = QString("statCommand%1").arg(menu_path); |
1804 | QMetaObject::invokeMethod(this, slot.toLatin1().constData(), Q_ARG(const char *, arg)QArgument<const char * >("const char *", arg), Q_ARG(void *, userdata)QArgument<void * >("void *", userdata)); |
1805 | } |
1806 | |
1807 | void WiresharkMainWindow::openTapParameterDialog(const QString cfg_str, const QString arg, void *userdata) |
1808 | { |
1809 | TapParameterDialog *tp_dialog = TapParameterDialog::showTapParameterStatistics(*this, capture_file_, cfg_str, arg, userdata); |
1810 | if (!tp_dialog) return; |
1811 | |
1812 | connect(tp_dialog, &TapParameterDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
1813 | connect(tp_dialog, &TapParameterDialog::updateFilter, df_combo_box_->lineEdit(), &QLineEdit::setText); |
1814 | tp_dialog->show(); |
1815 | } |
1816 | |
1817 | void WiresharkMainWindow::openTapParameterDialog() |
1818 | { |
1819 | QAction *tpa = qobject_cast<QAction *>(QObject::sender()); |
1820 | if (!tpa) return; |
1821 | |
1822 | const QString cfg_str = tpa->data().toString(); |
1823 | openTapParameterDialog(cfg_str, NULL__null, NULL__null); |
1824 | } |
1825 | |
1826 | #if defined(HAVE_SOFTWARE_UPDATE) && defined(Q_OS_WIN) |
1827 | void WiresharkMainWindow::softwareUpdateRequested() { |
1828 | // testCaptureFileClose doesn't use this string because we aren't |
1829 | // going to launch another dialog, but maybe we'll change that. |
1830 | QString before_what(tr(" before updating")); |
1831 | if (!testCaptureFileClose(before_what, Update)) { |
1832 | mainApp->rejectSoftwareUpdate(); |
1833 | } |
1834 | } |
1835 | #endif |
1836 | |
1837 | // File Menu |
1838 | |
1839 | void WiresharkMainWindow::connectFileMenuActions() |
1840 | { |
1841 | connect(main_ui_->actionFileOpen, &QAction::triggered, this, |
1842 | [this]() { openCaptureFile(); }); |
1843 | |
1844 | connect(main_ui_->actionFileMerge, &QAction::triggered, this, |
1845 | [this]() { mergeCaptureFile(); }); |
1846 | |
1847 | connect(main_ui_->actionFileImportFromHexDump, &QAction::triggered, this, |
1848 | [this]() { importCaptureFile(); }); |
1849 | |
1850 | connect(main_ui_->actionFileClose, &QAction::triggered, this, [this]() { |
1851 | QString before_what(tr(" before closing the file")); |
1852 | if (testCaptureFileClose(before_what)) { |
1853 | showWelcome(); |
1854 | } |
1855 | }); |
1856 | |
1857 | connect(main_ui_->actionFileSave, &QAction::triggered, this, |
1858 | [this]() { saveCaptureFile(capture_file_.capFile(), false); }); |
1859 | |
1860 | connect(main_ui_->actionFileSaveAs, &QAction::triggered, this, |
1861 | [this]() { saveAsCaptureFile(capture_file_.capFile()); }); |
1862 | |
1863 | connect(main_ui_->actionFileSetListFiles, &QAction::triggered, this, |
1864 | [this]() { file_set_dialog_->show(); }); |
1865 | |
1866 | connect(main_ui_->actionFileSetNextFile, &QAction::triggered, this, [this]() { |
1867 | fileset_entry *entry = fileset_get_next(); |
1868 | |
1869 | if (entry) { |
1870 | QString new_cf_path = entry->fullname; |
1871 | openCaptureFile(new_cf_path); |
1872 | } |
1873 | }); |
1874 | |
1875 | connect(main_ui_->actionFileSetPreviousFile, &QAction::triggered, this, [this]() { |
1876 | fileset_entry *entry = fileset_get_previous(); |
1877 | |
1878 | if (entry) { |
1879 | QString new_cf_path = entry->fullname; |
1880 | openCaptureFile(new_cf_path); |
1881 | } |
1882 | }); |
1883 | |
1884 | connect(main_ui_->actionFileExportPackets, &QAction::triggered, this, |
1885 | [this]() { exportSelectedPackets(); }); |
1886 | |
1887 | connect(main_ui_->actionFileExportAsPlainText, &QAction::triggered, this, |
1888 | [this]() { exportDissections(export_type_text); }); |
1889 | |
1890 | connect(main_ui_->actionFileExportAsCSV, &QAction::triggered, this, |
1891 | [this]() { exportDissections(export_type_csv); }); |
1892 | |
1893 | connect(main_ui_->actionFileExportAsCArrays, &QAction::triggered, this, |
1894 | [this]() { exportDissections(export_type_carrays); }); |
1895 | |
1896 | connect(main_ui_->actionFileExportAsPSML, &QAction::triggered, this, |
1897 | [this]() { exportDissections(export_type_psml); }); |
1898 | |
1899 | connect(main_ui_->actionFileExportAsPDML, &QAction::triggered, this, |
1900 | [this]() { exportDissections(export_type_pdml); }); |
1901 | |
1902 | connect(main_ui_->actionFileExportAsJSON, &QAction::triggered, this, |
1903 | [this]() { exportDissections(export_type_json); }); |
1904 | |
1905 | connect(main_ui_->actionFileExportPacketBytes, &QAction::triggered, this, |
1906 | [this]() { exportPacketBytes(); }, Qt::QueuedConnection); |
1907 | |
1908 | connect(main_ui_->actionFileExportPDU, &QAction::triggered, this, |
1909 | [this]() { exportPDU(); }); |
1910 | |
1911 | connect(main_ui_->actionFileStripHeaders, &QAction::triggered, this, |
1912 | [this]() { stripPacketHeaders(); }); |
1913 | |
1914 | connect(main_ui_->actionFileExportTLSSessionKeys, &QAction::triggered, this, |
1915 | [this]() { exportTLSSessionKeys(); }); |
1916 | |
1917 | connect(main_ui_->actionFilePrint, &QAction::triggered, this, |
1918 | [this]() { printFile(); }); |
1919 | } |
1920 | |
1921 | void WiresharkMainWindow::exportPacketBytes() |
1922 | { |
1923 | QString file_name; |
1924 | |
1925 | if (!capture_file_.capFile() || !capture_file_.capFile()->finfo_selected) return; |
1926 | |
1927 | file_name = WiresharkFileDialog::getSaveFileName(this, |
1928 | mainApp->windowTitleString(tr("Export Selected Packet Bytes")), |
1929 | mainApp->openDialogInitialDir().canonicalPath(), |
1930 | tr("Raw data (*.bin *.dat *.raw);;All Files (" ALL_FILES_WILDCARD"*" ")") |
1931 | ); |
1932 | |
1933 | if (file_name.length() > 0) { |
1934 | const uint8_t *data_p; |
1935 | |
1936 | data_p = tvb_get_ptr(capture_file_.capFile()->finfo_selected->ds_tvb, 0, -1) + |
1937 | capture_file_.capFile()->finfo_selected->start; |
1938 | write_file_binary_mode(qUtf8Printable(file_name)QtPrivate::asString(file_name).toUtf8().constData(), data_p, capture_file_.capFile()->finfo_selected->length); |
1939 | |
1940 | /* Save the directory name for future file dialogs. */ |
1941 | mainApp->setLastOpenDirFromFilename(file_name); |
1942 | } |
1943 | } |
1944 | |
1945 | void WiresharkMainWindow::exportPDU() |
1946 | { |
1947 | ExportPDUDialog *exportpdu_dialog = new ExportPDUDialog(this); |
1948 | |
1949 | if (exportpdu_dialog->isMinimized() == true) |
1950 | { |
1951 | exportpdu_dialog->showNormal(); |
1952 | } |
1953 | else |
1954 | { |
1955 | exportpdu_dialog->show(); |
1956 | } |
1957 | |
1958 | exportpdu_dialog->raise(); |
1959 | exportpdu_dialog->activateWindow(); |
1960 | } |
1961 | |
1962 | void WiresharkMainWindow::stripPacketHeaders() |
1963 | { |
1964 | StripHeadersDialog *stripheaders_dialog = new StripHeadersDialog(this); |
1965 | |
1966 | if (stripheaders_dialog->isMinimized() == true) |
1967 | { |
1968 | stripheaders_dialog->showNormal(); |
1969 | } |
1970 | else |
1971 | { |
1972 | stripheaders_dialog->show(); |
1973 | } |
1974 | |
1975 | stripheaders_dialog->raise(); |
1976 | stripheaders_dialog->activateWindow(); |
1977 | } |
1978 | |
1979 | |
1980 | void WiresharkMainWindow::exportTLSSessionKeys() |
1981 | { |
1982 | QString file_name; |
1983 | QString save_title; |
1984 | int keylist_len; |
1985 | |
1986 | keylist_len = ssl_session_key_count(); |
1987 | /* don't show up the dialog, if no data has to be saved */ |
1988 | if (keylist_len < 1) { |
1989 | /* shouldn't happen as the menu item should have been greyed out */ |
1990 | QMessageBox::warning( |
1991 | this, |
1992 | tr("No Keys"), |
1993 | tr("There are no TLS Session Keys to save."), |
1994 | QMessageBox::Ok |
1995 | ); |
1996 | return; |
1997 | } |
1998 | |
1999 | save_title.append(mainApp->windowTitleString(tr("Export TLS Session Keys (%Ln key(s))", "", keylist_len))); |
2000 | file_name = WiresharkFileDialog::getSaveFileName(this, |
2001 | save_title, |
2002 | mainApp->openDialogInitialDir().canonicalPath(), |
2003 | tr("TLS Session Keys (*.keys *.txt);;All Files (" ALL_FILES_WILDCARD"*" ")") |
2004 | ); |
2005 | if (file_name.length() > 0) { |
2006 | size_t keylist_length; |
2007 | char *keylist = ssl_export_sessions(&keylist_length); |
2008 | write_file_binary_mode(qUtf8Printable(file_name)QtPrivate::asString(file_name).toUtf8().constData(), keylist, keylist_length); |
2009 | |
2010 | /* Save the directory name for future file dialogs. */ |
2011 | mainApp->setLastOpenDirFromFilename(file_name); |
2012 | g_free(keylist); |
2013 | } |
2014 | } |
2015 | |
2016 | void WiresharkMainWindow::printFile() |
2017 | { |
2018 | capture_file *cf = capture_file_.capFile(); |
2019 | g_return_if_fail(cf)do { if ((cf)) { } else { g_return_if_fail_warning (((gchar*) 0), ((const char*) (__PRETTY_FUNCTION__)), "cf"); return; } } while (0); |
2020 | |
2021 | QList<int> rows = packet_list_->selectedRows(true); |
2022 | |
2023 | QStringList entries; |
2024 | foreach (int row, rows)for (auto _container_2024 = QtPrivate::qMakeForeachContainer( rows); _container_2024.i != _container_2024.e; ++_container_2024 .i) if (int row = *_container_2024.i; false) {} else |
2025 | entries << QString::number(row); |
2026 | QString selRange = entries.join(","); |
2027 | |
2028 | PrintDialog * pdlg_ = new PrintDialog(this, cf, selRange); |
2029 | pdlg_->setWindowModality(Qt::ApplicationModal); |
2030 | pdlg_->show(); |
2031 | } |
2032 | |
2033 | // Edit Menu |
2034 | |
2035 | void WiresharkMainWindow::connectEditMenuActions() |
2036 | { |
2037 | connect(main_ui_->actionCopyAllVisibleItems, &QAction::triggered, this, |
2038 | [this]() { copySelectedItems(CopyAllVisibleItems); }); |
2039 | |
2040 | connect(main_ui_->actionCopyListAsText, &QAction::triggered, this, |
2041 | [this]() { copySelectedItems(CopyListAsText); }); |
2042 | |
2043 | connect(main_ui_->actionCopyListAsCSV, &QAction::triggered, this, |
2044 | [this]() { copySelectedItems(CopyListAsCSV); }); |
2045 | |
2046 | connect(main_ui_->actionCopyListAsYAML, &QAction::triggered, this, |
2047 | [this]() { copySelectedItems(CopyListAsYAML); }); |
2048 | |
2049 | connect(main_ui_->actionCopyAllVisibleSelectedTreeItems, &QAction::triggered, this, |
2050 | [this]() { copySelectedItems(CopyAllVisibleSelectedTreeItems); }); |
2051 | |
2052 | connect(main_ui_->actionEditCopyDescription, &QAction::triggered, this, |
2053 | [this]() { copySelectedItems(CopySelectedDescription); }); |
2054 | |
2055 | connect(main_ui_->actionEditCopyFieldName, &QAction::triggered, this, |
2056 | [this]() { copySelectedItems(CopySelectedFieldName); }); |
2057 | |
2058 | connect(main_ui_->actionEditCopyValue, &QAction::triggered, this, |
2059 | [this]() { copySelectedItems(CopySelectedValue); }); |
2060 | |
2061 | connect(main_ui_->actionEditCopyAsFilter, &QAction::triggered, this, |
2062 | [this]() { matchFieldFilter(FilterAction::ActionCopy, FilterAction::ActionTypePlain); }); |
2063 | |
2064 | connect(main_ui_->actionEditFindPacket, &QAction::triggered, this, |
2065 | [this]() { findPacket(); }); |
2066 | |
2067 | connect(main_ui_->actionEditFindNext, &QAction::triggered, this, |
2068 | [this]() { main_ui_->searchFrame->findNext(); }); |
2069 | |
2070 | connect(main_ui_->actionEditFindPrevious, &QAction::triggered, this, |
2071 | [this]() { main_ui_->searchFrame->findPrevious(); }); |
2072 | |
2073 | // The items below are used in the packet list and detail context menus. |
2074 | // Use QueuedConnections so that the context menus aren't destroyed |
2075 | // prematurely. |
2076 | connect(main_ui_->actionEditMarkSelected, &QAction::triggered, this, [this]() { |
2077 | freeze(); |
2078 | packet_list_->markFrame(); |
2079 | thaw(); |
2080 | setMenusForSelectedPacket(); |
2081 | }, Qt::QueuedConnection); |
2082 | |
2083 | connect(main_ui_->actionEditMarkAllDisplayed, &QAction::triggered, this, [this]() { |
2084 | freeze(); |
2085 | packet_list_->markAllDisplayedFrames(true); |
2086 | thaw(); |
2087 | setMenusForSelectedPacket(); |
2088 | }, Qt::QueuedConnection); |
2089 | |
2090 | connect(main_ui_->actionEditUnmarkAllDisplayed, &QAction::triggered, this, [this]() { |
2091 | freeze(); |
2092 | packet_list_->markAllDisplayedFrames(false); |
2093 | thaw(); |
2094 | setMenusForSelectedPacket(); |
2095 | }, Qt::QueuedConnection); |
2096 | |
2097 | connect(main_ui_->actionEditNextMark, &QAction::triggered, this, [this]() { |
2098 | if (capture_file_.capFile()) { |
2099 | cf_find_packet_marked(capture_file_.capFile(), SD_FORWARD); |
2100 | } |
2101 | }, Qt::QueuedConnection); |
2102 | |
2103 | connect(main_ui_->actionEditPreviousMark, &QAction::triggered, this, [this]() { |
2104 | if (capture_file_.capFile()) { |
2105 | cf_find_packet_marked(capture_file_.capFile(), SD_BACKWARD); |
2106 | } |
2107 | }, Qt::QueuedConnection); |
2108 | |
2109 | connect(main_ui_->actionEditIgnoreSelected, &QAction::triggered, this, [this]() { |
2110 | freeze(); |
2111 | packet_list_->ignoreFrame(); |
2112 | thaw(); |
2113 | setMenusForSelectedPacket(); |
2114 | }, Qt::QueuedConnection); |
2115 | |
2116 | connect(main_ui_->actionEditIgnoreAllDisplayed, &QAction::triggered, this, [this]() { |
2117 | freeze(); |
2118 | packet_list_->ignoreAllDisplayedFrames(true); |
2119 | thaw(); |
2120 | setMenusForSelectedPacket(); |
2121 | }, Qt::QueuedConnection); |
2122 | |
2123 | connect(main_ui_->actionEditUnignoreAllDisplayed, &QAction::triggered, this, [this]() { |
2124 | freeze(); |
2125 | packet_list_->ignoreAllDisplayedFrames(false); |
2126 | thaw(); |
2127 | setMenusForSelectedPacket(); |
2128 | }, Qt::QueuedConnection); |
2129 | |
2130 | connect(main_ui_->actionEditSetTimeReference, &QAction::triggered, this, [this]() { |
2131 | packet_list_->setTimeReference(); |
2132 | setMenusForSelectedPacket(); |
2133 | }, Qt::QueuedConnection); |
2134 | |
2135 | connect(main_ui_->actionEditUnsetAllTimeReferences, &QAction::triggered, this, [this]() { |
2136 | packet_list_->unsetAllTimeReferences(); |
2137 | setMenusForSelectedPacket(); |
2138 | }, Qt::QueuedConnection); |
2139 | |
2140 | connect(main_ui_->actionEditNextTimeReference, &QAction::triggered, this, [this]() { |
2141 | if (!capture_file_.capFile()) return; |
2142 | cf_find_packet_time_reference(capture_file_.capFile(), SD_FORWARD); |
2143 | }, Qt::QueuedConnection); |
2144 | |
2145 | connect(main_ui_->actionEditPreviousTimeReference, &QAction::triggered, this, [this]() { |
2146 | if (!capture_file_.capFile()) return; |
2147 | cf_find_packet_time_reference(capture_file_.capFile(), SD_BACKWARD); |
2148 | }, Qt::QueuedConnection); |
2149 | |
2150 | connect(main_ui_->actionEditTimeShift, &QAction::triggered, this, |
2151 | [this]() { editTimeShift(); }, Qt::QueuedConnection); |
2152 | |
2153 | connect(main_ui_->actionDeleteAllPacketComments, &QAction::triggered, this, |
2154 | [this]() { deleteAllPacketComments(); }, Qt::QueuedConnection); |
2155 | |
2156 | connect(main_ui_->actionEditInjectSecrets, &QAction::triggered, this, |
2157 | [this]() { injectSecrets(); }, Qt::QueuedConnection); |
2158 | |
2159 | connect(main_ui_->actionEditDiscardAllSecrets, &QAction::triggered, this, |
2160 | [this]() { discardAllSecrets(); }, Qt::QueuedConnection); |
2161 | |
2162 | connect(main_ui_->actionEditConfigurationProfiles, &QAction::triggered, this, |
2163 | [this]() { editConfigurationProfiles(); }, Qt::QueuedConnection); |
2164 | |
2165 | connect(main_ui_->actionEditPreferences, &QAction::triggered, this, |
2166 | [this]() { showPreferencesDialog(PrefsModel::typeToString(PrefsModel::Appearance)); }, Qt::QueuedConnection); |
2167 | } |
2168 | |
2169 | // XXX This should probably be somewhere else. |
2170 | void WiresharkMainWindow::copySelectedItems(WiresharkMainWindow::CopySelected selection_type) |
2171 | { |
2172 | char label_str[ITEM_LABEL_LENGTH240]; |
2173 | QString clip; |
2174 | |
2175 | if (!capture_file_.capFile()) return; |
2176 | |
2177 | field_info *finfo_selected = capture_file_.capFile()->finfo_selected; |
2178 | |
2179 | switch (selection_type) { |
2180 | case CopySelectedDescription: |
2181 | if (proto_tree_->selectionModel()->hasSelection()) { |
2182 | QModelIndex idx = proto_tree_->selectionModel()->selectedIndexes().first(); |
2183 | clip = idx.data(Qt::DisplayRole).toString(); |
2184 | } |
2185 | break; |
2186 | case CopySelectedFieldName: |
2187 | if (finfo_selected && finfo_selected->hfinfo->abbrev != 0) { |
2188 | clip.append(finfo_selected->hfinfo->abbrev); |
2189 | } |
2190 | break; |
2191 | case CopySelectedValue: |
2192 | if (finfo_selected && capture_file_.capFile()->edt != 0) { |
2193 | char* field_str = get_node_field_value(finfo_selected, capture_file_.capFile()->edt); |
2194 | clip.append(field_str); |
2195 | g_free(field_str); |
2196 | } |
2197 | break; |
2198 | case CopyAllVisibleItems: |
2199 | clip = proto_tree_->toString(); |
2200 | break; |
2201 | case CopyAllVisibleSelectedTreeItems: |
2202 | if (proto_tree_->selectionModel()->hasSelection()) { |
2203 | clip = proto_tree_->toString(proto_tree_->selectionModel()->selectedIndexes().first()); |
2204 | } |
2205 | break; |
2206 | case CopyListAsText: |
2207 | case CopyListAsCSV: |
2208 | case CopyListAsYAML: |
2209 | if (packet_list_->selectedRows().count() > 0) |
2210 | { |
2211 | QList<int> rows = packet_list_->selectedRows(); |
2212 | QStringList content; |
2213 | |
2214 | PacketList::SummaryCopyType copyType = PacketList::CopyAsText; |
2215 | if (selection_type == CopyListAsCSV) |
2216 | copyType = PacketList::CopyAsCSV; |
2217 | else if (selection_type == CopyListAsYAML) |
2218 | copyType = PacketList::CopyAsYAML; |
2219 | |
2220 | if ((copyType == PacketList::CopyAsText) || |
2221 | (copyType == PacketList::CopyAsCSV)) { |
2222 | QString headerEntry = packet_list_->createHeaderSummaryText(copyType); |
2223 | content << headerEntry; |
2224 | } |
2225 | foreach (int row, rows)for (auto _container_2225 = QtPrivate::qMakeForeachContainer( rows); _container_2225.i != _container_2225.e; ++_container_2225 .i) if (int row = *_container_2225.i; false) {} else |
2226 | { |
2227 | QModelIndex idx = packet_list_->model()->index(row, 0); |
2228 | if (! idx.isValid()) |
2229 | continue; |
2230 | |
2231 | QString entry = packet_list_->createSummaryText(idx, copyType); |
2232 | content << entry; |
2233 | } |
2234 | |
2235 | if (content.count() > 0) { |
2236 | clip = content.join("\n"); |
2237 | // |
2238 | // Each YAML item ends with a newline, so the string |
2239 | // ends with a newline already if it's CopyListAsYAML. |
2240 | // If we add a newline, there'd be an extra blank |
2241 | // line. |
2242 | // |
2243 | // Otherwise, we've used newlines as separators, not |
2244 | // terminators, so there's no final newline. Add it. |
2245 | // |
2246 | if (selection_type != CopyListAsYAML) |
2247 | clip += "\n"; |
2248 | } |
2249 | } |
2250 | break; |
2251 | } |
2252 | |
2253 | if (clip.length() == 0) { |
2254 | /* If no representation then... Try to read the value */ |
2255 | proto_item_fill_label(capture_file_.capFile()->finfo_selected, label_str); |
2256 | clip.append(label_str); |
2257 | } |
2258 | |
2259 | if (clip.length()) { |
2260 | mainApp->clipboard()->setText(clip); |
2261 | } else { |
2262 | QString err = tr("Couldn't copy text. Try another item."); |
2263 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, err); |
2264 | } |
2265 | } |
2266 | |
2267 | void WiresharkMainWindow::findPacket() |
2268 | { |
2269 | if (! packet_list_->model() || packet_list_->model()->rowCount() < 1) { |
2270 | return; |
2271 | } |
2272 | setPreviousFocus(); |
2273 | if (!main_ui_->searchFrame->isVisible()) { |
2274 | showAccordionFrame(main_ui_->searchFrame, true); |
2275 | } else { |
2276 | main_ui_->searchFrame->animatedHide(); |
2277 | } |
2278 | main_ui_->searchFrame->setFocus(); |
2279 | } |
2280 | |
2281 | void WiresharkMainWindow::editTimeShift() |
2282 | { |
2283 | TimeShiftDialog *ts_dialog = new TimeShiftDialog(this, capture_file_.capFile()); |
2284 | connect(ts_dialog, &TimeShiftDialog::finished, this, &WiresharkMainWindow::editTimeShiftFinished); |
2285 | |
2286 | connect(this, &WiresharkMainWindow::setCaptureFile, ts_dialog, &TimeShiftDialog::setCaptureFile); |
2287 | connect(ts_dialog, &TimeShiftDialog::timeShifted, packet_list_, &PacketList::applyTimeShift, Qt::QueuedConnection); |
2288 | |
2289 | ts_dialog->setWindowModality(Qt::ApplicationModal); |
2290 | ts_dialog->setAttribute(Qt::WA_DeleteOnClose); |
2291 | ts_dialog->show(); |
2292 | } |
2293 | |
2294 | void WiresharkMainWindow::editTimeShiftFinished(int) |
2295 | { |
2296 | if (capture_file_.capFile()->unsaved_changes) { |
2297 | updateForUnsavedChanges(); |
2298 | } |
2299 | } |
2300 | |
2301 | void WiresharkMainWindow::addPacketComment() |
2302 | { |
2303 | QList<int> rows = selectedRows(); |
2304 | if (rows.count() == 0) |
2305 | return; |
2306 | |
2307 | frame_data * fdata = frameDataForRow(rows.at(0)); |
2308 | if (! fdata) |
2309 | return; |
2310 | |
2311 | PacketCommentDialog* pc_dialog; |
2312 | pc_dialog = new PacketCommentDialog(false, this, NULL__null); |
2313 | connect(pc_dialog, &QDialog::finished, std::bind(&WiresharkMainWindow::addPacketCommentFinished, this, pc_dialog, std::placeholders::_1)); |
2314 | pc_dialog->setWindowModality(Qt::ApplicationModal); |
2315 | pc_dialog->setAttribute(Qt::WA_DeleteOnClose); |
2316 | pc_dialog->show(); |
2317 | } |
2318 | |
2319 | void WiresharkMainWindow::addPacketCommentFinished(PacketCommentDialog* pc_dialog _U___attribute__((unused)), int result _U___attribute__((unused))) |
2320 | { |
2321 | if (result == QDialog::Accepted) { |
2322 | packet_list_->addPacketComment(pc_dialog->text()); |
2323 | updateForUnsavedChanges(); |
2324 | } |
2325 | } |
2326 | |
2327 | void WiresharkMainWindow::editPacketComment() |
2328 | { |
2329 | QList<int> rows = selectedRows(); |
2330 | if (rows.count() != 1) |
2331 | return; |
2332 | |
2333 | QAction *ra = qobject_cast<QAction*>(sender()); |
2334 | unsigned nComment = ra->data().toUInt(); |
2335 | PacketCommentDialog* pc_dialog; |
2336 | pc_dialog = new PacketCommentDialog(true, this, packet_list_->getPacketComment(nComment)); |
2337 | connect(pc_dialog, &QDialog::finished, std::bind(&WiresharkMainWindow::editPacketCommentFinished, this, pc_dialog, std::placeholders::_1, nComment)); |
2338 | pc_dialog->setWindowModality(Qt::ApplicationModal); |
2339 | pc_dialog->setAttribute(Qt::WA_DeleteOnClose); |
2340 | pc_dialog->show(); |
2341 | } |
2342 | |
2343 | void WiresharkMainWindow::editPacketCommentFinished(PacketCommentDialog* pc_dialog _U___attribute__((unused)), int result _U___attribute__((unused)), unsigned nComment) |
2344 | { |
2345 | if (result == QDialog::Accepted) { |
2346 | packet_list_->setPacketComment(nComment, pc_dialog->text()); |
2347 | updateForUnsavedChanges(); |
2348 | } |
2349 | } |
2350 | |
2351 | void WiresharkMainWindow::deletePacketComment() |
2352 | { |
2353 | QAction *ra = qobject_cast<QAction*>(sender()); |
2354 | unsigned nComment = ra->data().toUInt(); |
2355 | packet_list_->setPacketComment(nComment, QString("")); |
2356 | updateForUnsavedChanges(); |
2357 | } |
2358 | |
2359 | void WiresharkMainWindow::deleteCommentsFromPackets() |
2360 | { |
2361 | packet_list_->deleteCommentsFromPackets(); |
2362 | updateForUnsavedChanges(); |
2363 | } |
2364 | |
2365 | void WiresharkMainWindow::deleteAllPacketComments() |
2366 | { |
2367 | QMessageBox *msg_dialog = new QMessageBox(); |
2368 | connect(msg_dialog, &QMessageBox::finished, this, &WiresharkMainWindow::deleteAllPacketCommentsFinished); |
2369 | |
2370 | msg_dialog->setIcon(QMessageBox::Question); |
2371 | msg_dialog->setText(tr("Are you sure you want to remove all packet comments?")); |
2372 | |
2373 | msg_dialog->setStandardButtons(QMessageBox::Ok | QMessageBox::Cancel); |
2374 | msg_dialog->setDefaultButton(QMessageBox::Ok); |
2375 | |
2376 | msg_dialog->setWindowModality(Qt::ApplicationModal); |
2377 | msg_dialog->setAttribute(Qt::WA_DeleteOnClose); |
2378 | msg_dialog->show(); |
2379 | } |
2380 | |
2381 | void WiresharkMainWindow::deleteAllPacketCommentsFinished(int result) |
2382 | { |
2383 | if (result == QMessageBox::Ok) { |
2384 | /* XXX Do we need a wait/hourglass for large files? */ |
2385 | packet_list_->deleteAllPacketComments(); |
2386 | updateForUnsavedChanges(); |
2387 | } |
2388 | } |
2389 | |
2390 | void WiresharkMainWindow::injectSecrets() |
2391 | { |
2392 | int keylist_len; |
2393 | |
2394 | keylist_len = ssl_session_key_count(); |
2395 | /* don't do anything if no data has to be saved */ |
2396 | if (keylist_len < 1) { |
2397 | QMessageBox::Button ret = QMessageBox::warning( |
2398 | this, |
2399 | tr("No TLS Secrets"), |
2400 | tr("There are no available secrets used to decrypt TLS traffic in the capture file.\ |
2401 | Would you like to view information about how to decrypt TLS traffic on the wiki?"), |
2402 | QMessageBox::Yes | QMessageBox::No, |
2403 | QMessageBox::No); |
2404 | |
2405 | if (ret != QMessageBox::Yes) return; |
2406 | |
2407 | QUrl wiki_url = QString(WS_WIKI_URL("TLS#tls-decryption")"https://wiki.wireshark.org" "/" "TLS#tls-decryption"); |
2408 | QDesktopServices::openUrl(wiki_url); |
2409 | return; |
2410 | } |
2411 | |
2412 | if (!capture_file_.isValid()) |
2413 | return; |
2414 | |
2415 | /* XXX: It would be nice to handle other types of secrets that |
2416 | * can be written to a DSB, maybe have a proper dialog. |
2417 | */ |
2418 | capture_file *cf = capture_file_.capFile(); |
2419 | tls_export_dsb(cf); |
2420 | updateForUnsavedChanges(); |
2421 | } |
2422 | |
2423 | void WiresharkMainWindow::discardAllSecrets() |
2424 | { |
2425 | if (!capture_file_.isValid()) |
2426 | return; |
2427 | |
2428 | QMessageBox* msg_dialog = new QMessageBox(); |
2429 | connect(msg_dialog, &QMessageBox::finished, this, &WiresharkMainWindow::discardAllSecretsFinished); |
2430 | |
2431 | msg_dialog->setIcon(QMessageBox::Question); |
2432 | msg_dialog->setText(tr("Are you sure you want to discard all decryption secrets?")); |
2433 | |
2434 | msg_dialog->setStandardButtons(QMessageBox::Ok | QMessageBox::Cancel); |
2435 | msg_dialog->setDefaultButton(QMessageBox::Ok); |
2436 | |
2437 | msg_dialog->setWindowModality(Qt::ApplicationModal); |
2438 | msg_dialog->setAttribute(Qt::WA_DeleteOnClose); |
2439 | msg_dialog->show(); |
2440 | } |
2441 | |
2442 | void WiresharkMainWindow::discardAllSecretsFinished(int result) |
2443 | { |
2444 | if (result == QMessageBox::Ok) { |
2445 | /* XXX: It would be nice to handle other types of secrets that |
2446 | * can be written to a DSB, maybe have a proper dialog. |
2447 | */ |
2448 | capture_file* cf = capture_file_.capFile(); |
2449 | if (wtap_file_discard_decryption_secrets(cf->provider.wth)) { |
2450 | cf->unsaved_changes = true; |
2451 | updateForUnsavedChanges(); |
2452 | } |
2453 | } |
2454 | } |
2455 | |
2456 | void WiresharkMainWindow::editConfigurationProfiles() |
2457 | { |
2458 | ProfileDialog *cp_dialog = new ProfileDialog(); |
2459 | cp_dialog->setWindowModality(Qt::ApplicationModal); |
2460 | cp_dialog->setAttribute(Qt::WA_DeleteOnClose); |
2461 | cp_dialog->show(); |
2462 | } |
2463 | |
2464 | void WiresharkMainWindow::showPreferencesDialog(QString module_name) |
2465 | { |
2466 | PreferencesDialog *pref_dialog = new PreferencesDialog(this); |
2467 | connect(pref_dialog, &PreferencesDialog::destroyed, mainApp, &MainApplication::flushAppSignals); |
2468 | saveWindowGeometry(); // Save in case the layout panes are rearranged |
2469 | |
2470 | pref_dialog->setPane(module_name); |
2471 | pref_dialog->setWindowModality(Qt::ApplicationModal); |
2472 | pref_dialog->setAttribute(Qt::WA_DeleteOnClose); |
2473 | pref_dialog->show(); |
2474 | } |
2475 | |
2476 | // View Menu |
2477 | |
2478 | void WiresharkMainWindow::connectViewMenuActions() |
2479 | { |
2480 | connect(main_ui_->actionViewFullScreen, &QAction::triggered, this, [this](bool checked) { |
2481 | if (checked) { |
2482 | // Save the state for future restore |
2483 | was_maximized_ = this->isMaximized(); |
2484 | this->showFullScreen(); |
2485 | } else { |
2486 | // Restore the previous state |
2487 | if (was_maximized_) { |
2488 | this->showMaximized(); |
2489 | } else { |
2490 | this->showNormal(); |
2491 | } |
2492 | } |
2493 | }); |
2494 | |
2495 | connect(main_ui_->actionViewTimeDisplaySecondsWithHoursAndMinutes, &QAction::triggered, this, |
2496 | [this](bool checked) { setTimeDisplaySecondsWithHoursAndMinutes(checked); }); |
2497 | |
2498 | connect(main_ui_->actionViewEditResolvedName, &QAction::triggered, this, |
2499 | [this]() { editResolvedName(); }); |
2500 | |
2501 | connect(main_ui_->actionViewNameResolutionPhysical, &QAction::triggered, this, |
2502 | [this]() { setNameResolution(); }); |
2503 | |
2504 | connect(main_ui_->actionViewNameResolutionNetwork, &QAction::triggered, this, |
2505 | [this]() { setNameResolution(); }); |
2506 | |
2507 | connect(main_ui_->actionViewNameResolutionTransport, &QAction::triggered, this, |
2508 | [this]() { setNameResolution(); }); |
2509 | |
2510 | connect(main_ui_->actionViewZoomIn, &QAction::triggered, this, [this]() { |
2511 | recent.gui_zoom_level++; |
2512 | zoomText(); |
2513 | }); |
2514 | |
2515 | connect(main_ui_->actionViewZoomOut, &QAction::triggered, this, [this]() { |
2516 | recent.gui_zoom_level--; |
2517 | zoomText(); |
2518 | }); |
2519 | |
2520 | connect(main_ui_->actionViewNormalSize, &QAction::triggered, this, [this]() { |
2521 | recent.gui_zoom_level = 0; |
2522 | zoomText(); |
2523 | }); |
2524 | |
2525 | connect(main_ui_->actionViewExpandSubtrees, &QAction::triggered, |
2526 | proto_tree_, &ProtoTree::expandSubtrees); |
2527 | |
2528 | connect(main_ui_->actionViewCollapseSubtrees, &QAction::triggered, |
2529 | proto_tree_, &ProtoTree::collapseSubtrees); |
2530 | |
2531 | connect(main_ui_->actionViewExpandAll, &QAction::triggered, |
2532 | proto_tree_, &ProtoTree::expandAll); |
2533 | |
2534 | connect(main_ui_->actionViewCollapseAll, &QAction::triggered, |
2535 | proto_tree_, &ProtoTree::collapseAll); |
2536 | |
2537 | connect(main_ui_->actionViewColorizePacketList, &QAction::triggered, this, [this](bool checked) { |
2538 | recent.packet_list_colorize = checked; |
2539 | packet_list_->recolorPackets(); |
2540 | }); |
2541 | |
2542 | connect(main_ui_->actionViewColoringRules, &QAction::triggered, this, |
2543 | [this]() { showColoringRulesDialog(); }); |
2544 | |
2545 | connect(main_ui_->actionViewColorizeResetColorization, &QAction::triggered, this, [this]() { |
2546 | char *err_msg = NULL__null; |
2547 | if (!color_filters_reset_tmp(&err_msg)) { |
2548 | simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK0x01, "%s", err_msg); |
2549 | g_free(err_msg); |
2550 | } |
2551 | packet_list_->recolorPackets(); |
2552 | setMenusForSelectedPacket(); |
2553 | }); |
2554 | |
2555 | connect(main_ui_->actionViewColorizeNewColoringRule, &QAction::triggered, this, |
2556 | [this]() { colorizeConversation(true); }); |
2557 | |
2558 | connect(main_ui_->actionViewResetLayout, &QAction::triggered, this, [this]() { |
2559 | recent.gui_geometry_main_upper_pane = 0; |
2560 | recent.gui_geometry_main_lower_pane = 0; |
2561 | g_free(recent.gui_geometry_main_master_split); |
2562 | g_free(recent.gui_geometry_main_extra_split); |
2563 | recent.gui_geometry_main_master_split = NULL__null; |
2564 | recent.gui_geometry_main_extra_split = NULL__null; |
2565 | applyRecentPaneGeometry(); |
2566 | }); |
2567 | |
2568 | connect(main_ui_->actionViewResizeColumns, &QAction::triggered, this, [this]() { |
2569 | if (! packet_list_->model()) |
2570 | return; |
2571 | for (int col = 0; col < packet_list_->model()->columnCount(); col++) { |
2572 | packet_list_->resizeColumnToContents(col); |
2573 | recent_set_column_width(col, packet_list_->columnWidth(col)); |
2574 | } |
2575 | }); |
2576 | |
2577 | connect(main_ui_->actionViewInternalsConversationHashTables, &QAction::triggered, this, [this]() { |
2578 | ConversationHashTablesDialog *conversation_hash_tables_dlg = new ConversationHashTablesDialog(this); |
2579 | conversation_hash_tables_dlg->show(); |
2580 | }); |
2581 | |
2582 | connect(main_ui_->actionViewInternalsDissectorTables, &QAction::triggered, this, [this]() { |
2583 | DissectorTablesDialog *dissector_tables_dlg = new DissectorTablesDialog(this); |
2584 | dissector_tables_dlg->show(); |
2585 | }); |
2586 | |
2587 | connect(main_ui_->actionViewInternalsSupportedProtocols, &QAction::triggered, this, [this]() { |
2588 | SupportedProtocolsDialog *supported_protocols_dlg = new SupportedProtocolsDialog(this); |
2589 | supported_protocols_dlg->show(); |
2590 | }); |
2591 | |
2592 | connect(main_ui_->actionViewShowPacketInNewWindow, &QAction::triggered, this, |
2593 | [this]() { openPacketDialog(); }); |
2594 | |
2595 | // This is only used in ProtoTree. Defining it here makes more sense. |
2596 | connect(main_ui_->actionContextShowLinkedPacketInNewWindow, &QAction::triggered, this, |
2597 | [this]() { openPacketDialog(true); }); |
2598 | |
2599 | connect(main_ui_->actionViewReload_as_File_Format_or_Capture, &QAction::triggered, this, |
2600 | [this]() { reloadCaptureFileAsFormatOrCapture(); }); |
2601 | |
2602 | connect(main_ui_->actionViewReload, &QAction::triggered, this, |
2603 | [this]() { reloadCaptureFile(); }); |
2604 | } |
2605 | |
2606 | void WiresharkMainWindow::showHideMainWidgets(QAction *action) |
2607 | { |
2608 | if (!action) { |
2609 | return; |
2610 | } |
2611 | bool show = action->isChecked(); |
2612 | QWidget *widget = action->data().value<QWidget*>(); |
2613 | |
2614 | // We may have come from the toolbar context menu, so check/uncheck each |
2615 | // action as well. |
2616 | if (widget == main_ui_->mainToolBar) { |
2617 | recent.main_toolbar_show = show; |
2618 | main_ui_->actionViewMainToolbar->setChecked(show); |
2619 | } else if (widget == main_ui_->displayFilterToolBar) { |
2620 | recent.filter_toolbar_show = show; |
2621 | main_ui_->actionViewFilterToolbar->setChecked(show); |
2622 | #if defined(HAVE_LIBNL1) && defined(HAVE_NL802111) |
2623 | } else if (widget == main_ui_->wirelessToolBar) { |
2624 | recent.wireless_toolbar_show = show; |
2625 | main_ui_->actionViewWirelessToolbar->setChecked(show); |
2626 | #endif |
2627 | } else if (widget == main_ui_->statusBar) { |
2628 | recent.statusbar_show = show; |
2629 | main_ui_->actionViewStatusBar->setChecked(show); |
2630 | } else if (widget == packet_list_) { |
2631 | recent.packet_list_show = show; |
2632 | main_ui_->actionViewPacketList->setChecked(show); |
2633 | } else if (widget == proto_tree_) { |
2634 | recent.tree_view_show = show; |
2635 | main_ui_->actionViewPacketDetails->setChecked(show); |
2636 | } else if (widget == byte_view_tab_) { |
2637 | recent.byte_view_show = show; |
2638 | main_ui_->actionViewPacketBytes->setChecked(show); |
2639 | } else if (widget == packet_diagram_) { |
2640 | recent.packet_diagram_show = show; |
2641 | main_ui_->actionViewPacketDiagram->setChecked(show); |
2642 | } else { |
2643 | foreach(QAction *action, main_ui_->menuInterfaceToolbars->actions())for (auto _container_2643 = QtPrivate::qMakeForeachContainer( main_ui_->menuInterfaceToolbars->actions()); _container_2643 .i != _container_2643.e; ++_container_2643.i) if (QAction *action = *_container_2643.i; false) {} else { |
2644 | QToolBar *toolbar = action->data().value<QToolBar *>(); |
2645 | if (widget == toolbar) { |
2646 | GList *entry = g_list_find_custom(recent.interface_toolbars, action->text().toUtf8(), (GCompareFunc)strcmp); |
2647 | if (show && !entry) { |
2648 | recent.interface_toolbars = g_list_append(recent.interface_toolbars, qstring_strdup(action->text())); |
2649 | } else if (!show && entry) { |
2650 | recent.interface_toolbars = g_list_remove(recent.interface_toolbars, entry->data); |
2651 | } |
2652 | action->setChecked(show); |
2653 | } |
2654 | } |
2655 | |
2656 | ext_toolbar_t * toolbar = VariantPointer<ext_toolbar_t>::asPtr(action->data()); |
2657 | if (toolbar) { |
2658 | GList *entry = g_list_find_custom(recent.gui_additional_toolbars, toolbar->name, (GCompareFunc)strcmp); |
2659 | if (show && !entry) { |
2660 | recent.gui_additional_toolbars = g_list_append(recent.gui_additional_toolbars, g_strdup(toolbar->name)g_strdup_inline (toolbar->name)); |
2661 | } else if (!show && entry) { |
2662 | recent.gui_additional_toolbars = g_list_remove(recent.gui_additional_toolbars, entry->data); |
2663 | } |
2664 | action->setChecked(show); |
2665 | |
2666 | QList<QToolBar *> toolbars = findChildren<QToolBar *>(); |
2667 | foreach(QToolBar *bar, toolbars)for (auto _container_2667 = QtPrivate::qMakeForeachContainer( toolbars); _container_2667.i != _container_2667.e; ++_container_2667 .i) if (QToolBar *bar = *_container_2667.i; false) {} else { |
2668 | AdditionalToolBar *iftoolbar = dynamic_cast<AdditionalToolBar *>(bar); |
2669 | if (iftoolbar && iftoolbar->menuName().compare(toolbar->name) == 0) { |
2670 | iftoolbar->setVisible(show); |
2671 | } |
2672 | } |
2673 | } |
2674 | } |
2675 | |
2676 | if (widget) { |
2677 | widget->setVisible(show); |
2678 | } |
2679 | } |
2680 | |
2681 | void WiresharkMainWindow::setTimestampFormat(QAction *action) |
2682 | { |
2683 | if (!action) { |
2684 | return; |
2685 | } |
2686 | ts_type tsf = action->data().value<ts_type>(); |
2687 | if (recent.gui_time_format != tsf) { |
2688 | timestamp_set_type(tsf); |
2689 | recent.gui_time_format = tsf; |
2690 | |
2691 | if (packet_list_) { |
2692 | packet_list_->resetColumns(); |
2693 | packet_list_->resizeAllColumns(true); |
2694 | } |
2695 | } |
2696 | } |
2697 | |
2698 | void WiresharkMainWindow::setTimestampPrecision(QAction *action) |
2699 | { |
2700 | if (!action) { |
2701 | return; |
2702 | } |
2703 | ts_precision tsp = action->data().value<ts_precision>(); |
2704 | if (recent.gui_time_precision != tsp) { |
2705 | timestamp_set_precision(tsp); |
2706 | recent.gui_time_precision = tsp; |
2707 | |
2708 | if (packet_list_) { |
2709 | packet_list_->resetColumns(); |
2710 | packet_list_->resizeAllColumns(true); |
2711 | } |
2712 | } |
2713 | } |
2714 | |
2715 | void WiresharkMainWindow::setTimeDisplaySecondsWithHoursAndMinutes(bool checked) |
2716 | { |
2717 | if (checked) { |
2718 | recent.gui_seconds_format = TS_SECONDS_HOUR_MIN_SEC; |
2719 | } else { |
2720 | recent.gui_seconds_format = TS_SECONDS_DEFAULT; |
2721 | } |
2722 | timestamp_set_seconds_type(recent.gui_seconds_format); |
2723 | |
2724 | if (packet_list_) { |
2725 | packet_list_->resetColumns(); |
2726 | packet_list_->resizeAllColumns(true); |
2727 | } |
2728 | } |
2729 | |
2730 | void WiresharkMainWindow::editResolvedName() |
2731 | { |
2732 | //int column = packet_list_->selectedColumn(); |
2733 | int column = -1; |
2734 | |
2735 | if (packet_list_->contextMenuActive() || packet_list_->hasFocus()) { |
2736 | if (packet_list_->currentIndex().isValid()) { |
2737 | column = packet_list_->currentIndex().column(); |
2738 | } |
2739 | } |
2740 | |
2741 | main_ui_->addressEditorFrame->editAddresses(capture_file_, column); |
2742 | showAccordionFrame(main_ui_->addressEditorFrame); |
2743 | } |
2744 | |
2745 | void WiresharkMainWindow::setNameResolution() |
2746 | { |
2747 | gbl_resolv_flags.mac_name = main_ui_->actionViewNameResolutionPhysical->isChecked() ? true : false; |
2748 | gbl_resolv_flags.network_name = main_ui_->actionViewNameResolutionNetwork->isChecked() ? true : false; |
2749 | gbl_resolv_flags.transport_name = main_ui_->actionViewNameResolutionTransport->isChecked() ? true : false; |
2750 | |
2751 | if (packet_list_) { |
2752 | packet_list_->resetColumns(); |
2753 | } |
2754 | mainApp->emitAppSignal(WiresharkApplication::NameResolutionChanged); |
2755 | } |
2756 | |
2757 | void WiresharkMainWindow::zoomText() |
2758 | { |
2759 | mainApp->zoomTextFont(recent.gui_zoom_level); |
2760 | } |
2761 | |
2762 | void WiresharkMainWindow::showColoringRulesDialog() |
2763 | { |
2764 | ColoringRulesDialog *coloring_rules_dialog = new ColoringRulesDialog(this); |
2765 | connect(coloring_rules_dialog, &ColoringRulesDialog::accepted, |
2766 | packet_list_, &PacketList::recolorPackets); |
2767 | connect(coloring_rules_dialog, &ColoringRulesDialog::filterAction, |
2768 | this, &WiresharkMainWindow::filterAction); |
2769 | |
2770 | coloring_rules_dialog->setWindowModality(Qt::ApplicationModal); |
2771 | coloring_rules_dialog->setAttribute(Qt::WA_DeleteOnClose); |
2772 | coloring_rules_dialog->show(); |
2773 | } |
2774 | |
2775 | // actionViewColorizeConversation1 - 10 |
2776 | void WiresharkMainWindow::colorizeConversation(bool create_rule) |
2777 | { |
2778 | QAction *colorize_action = qobject_cast<QAction *>(sender()); |
2779 | if (!colorize_action) return; |
2780 | |
2781 | if (capture_file_.capFile() && selectedRows().count() > 0) { |
2782 | packet_info *pi = capture_file_.packetInfo(); |
2783 | uint8_t cc_num = colorize_action->data().toUInt(); |
2784 | char *filter = conversation_filter_from_packet(pi); |
2785 | if (filter == NULL__null) { |
2786 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, tr("Unable to build conversation filter.")); |
2787 | return; |
2788 | } |
2789 | |
2790 | if (create_rule) { |
2791 | ColoringRulesDialog coloring_rules_dialog(this, filter); |
2792 | connect(&coloring_rules_dialog, &ColoringRulesDialog::accepted, |
2793 | packet_list_, &PacketList::recolorPackets); |
2794 | connect(&coloring_rules_dialog, &ColoringRulesDialog::filterAction, |
2795 | this, &WiresharkMainWindow::filterAction); |
2796 | coloring_rules_dialog.exec(); |
2797 | } else { |
2798 | char *err_msg = NULL__null; |
2799 | if (!color_filters_set_tmp(cc_num, filter, false, &err_msg)) { |
2800 | simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK0x01, "%s", err_msg); |
2801 | g_free(err_msg); |
2802 | } |
2803 | packet_list_->recolorPackets(); |
2804 | } |
2805 | } |
2806 | setMenusForSelectedPacket(); |
2807 | } |
2808 | |
2809 | void WiresharkMainWindow::colorizeActionTriggered() |
2810 | { |
2811 | QByteArray filter; |
2812 | int color_number = -1; |
2813 | |
2814 | ConversationAction *conv_action = qobject_cast<ConversationAction *>(sender()); |
2815 | if (conv_action) { |
2816 | filter = conv_action->filter(); |
2817 | color_number = conv_action->colorNumber(); |
2818 | } else { |
2819 | ColorizeAction *colorize_action = qobject_cast<ColorizeAction *>(sender()); |
2820 | if (colorize_action) { |
2821 | filter = colorize_action->filter(); |
2822 | color_number = colorize_action->colorNumber(); |
2823 | } |
2824 | } |
2825 | |
2826 | colorizeWithFilter(filter, color_number); |
2827 | } |
2828 | |
2829 | void WiresharkMainWindow::colorizeWithFilter(QByteArray filter, int color_number) |
2830 | { |
2831 | if (filter.isEmpty()) return; |
2832 | |
2833 | if (color_number > 0) { |
2834 | // Assume "Color X" |
2835 | char *err_msg = NULL__null; |
2836 | if (!color_filters_set_tmp(color_number, filter.constData(), false, &err_msg)) { |
2837 | simple_dialog(ESD_TYPE_ERROR, ESD_BTN_OK0x01, "%s", err_msg); |
2838 | g_free(err_msg); |
2839 | } |
2840 | packet_list_->recolorPackets(); |
2841 | } else { |
2842 | // New coloring rule |
2843 | ColoringRulesDialog coloring_rules_dialog(window(), filter); |
2844 | connect(&coloring_rules_dialog, &ColoringRulesDialog::accepted, |
2845 | packet_list_, &PacketList::recolorPackets); |
2846 | connect(&coloring_rules_dialog, &ColoringRulesDialog::filterAction, |
2847 | this, &WiresharkMainWindow::filterAction); |
2848 | coloring_rules_dialog.exec(); |
2849 | } |
2850 | main_ui_->actionViewColorizeResetColorization->setEnabled(tmp_color_filters_used()); |
2851 | } |
2852 | |
2853 | void WiresharkMainWindow::openPacketDialog(bool from_reference) |
2854 | { |
2855 | frame_data * fdata = Q_NULLPTRnullptr; |
2856 | |
2857 | /* Find the frame for which we're popping up a dialog */ |
2858 | if (from_reference) { |
2859 | uint32_t framenum = fvalue_get_uinteger(capture_file_.capFile()->finfo_selected->value); |
2860 | if (framenum == 0) |
2861 | return; |
2862 | |
2863 | fdata = frame_data_sequence_find(capture_file_.capFile()->provider.frames, framenum); |
2864 | } else if (selectedRows().count() == 1) { |
2865 | fdata = frameDataForRow(selectedRows().at(0)); |
2866 | } else if (selectedRows().count() > 1) |
2867 | return; |
2868 | |
2869 | /* If we have a frame, pop up the dialog */ |
2870 | if (fdata) { |
2871 | PacketDialog *packet_dialog = new PacketDialog(*this, capture_file_, fdata); |
2872 | |
2873 | connect(packet_dialog, &PacketDialog::showProtocolPreferences, |
2874 | this, &WiresharkMainWindow::showPreferencesDialog); |
2875 | connect(packet_dialog, SIGNAL(editProtocolPreference(preference*, pref_module*))qFlagLocation("2" "editProtocolPreference(preference*, pref_module*)" "\0" "ui/qt/wireshark_main_window_slots.cpp" ":" "2875"), |
2876 | main_ui_->preferenceEditorFrame, SLOT(editPreference(preference*, pref_module*))qFlagLocation("1" "editPreference(preference*, pref_module*)" "\0" "ui/qt/wireshark_main_window_slots.cpp" ":" "2876")); |
2877 | |
2878 | connect(this, &WiresharkMainWindow::closePacketDialogs, packet_dialog, &PacketDialog::close); |
2879 | zoomText(); // Emits mainApp->zoomMonospaceFont(QFont) |
2880 | |
2881 | packet_dialog->show(); |
2882 | } |
2883 | } |
2884 | |
2885 | void WiresharkMainWindow::reloadCaptureFileAsFormatOrCapture() |
2886 | { |
2887 | capture_file *cf = CaptureFile::globalCapFile(); |
2888 | |
2889 | if (cf->unsaved_changes) { |
2890 | QString before_what(tr(" before reloading the file")); |
2891 | if (!testCaptureFileClose(before_what, Reload)) |
2892 | return; |
2893 | } |
2894 | |
2895 | if (cf->open_type == WTAP_TYPE_AUTO0) |
2896 | cf->open_type = open_info_name_to_type("MIME Files Format"); |
2897 | else /* TODO: This should be latest format chosen by user */ |
2898 | cf->open_type = WTAP_TYPE_AUTO0; |
2899 | |
2900 | cf_reload(cf); |
2901 | } |
2902 | |
2903 | void WiresharkMainWindow::reloadCaptureFile() |
2904 | { |
2905 | capture_file *cf = CaptureFile::globalCapFile(); |
2906 | |
2907 | if (cf->unsaved_changes) { |
2908 | QString before_what(tr(" before reloading the file")); |
2909 | if (!testCaptureFileClose(before_what, Reload)) |
2910 | return; |
2911 | } |
2912 | |
2913 | cf_reload(cf); |
2914 | } |
2915 | |
2916 | |
2917 | // Expand / collapse slots in proto_tree |
2918 | |
2919 | // Go Menu |
2920 | |
2921 | void WiresharkMainWindow::connectGoMenuActions() |
2922 | { |
2923 | connect(main_ui_->actionGoGoToPacket, &QAction::triggered, this, [this]() { |
2924 | if (! packet_list_->model() || packet_list_->model()->rowCount() < 1) { |
2925 | return; |
2926 | } |
2927 | setPreviousFocus(); |
2928 | |
2929 | showAccordionFrame(main_ui_->goToFrame, true); |
2930 | if (main_ui_->goToFrame->isVisible()) { |
2931 | main_ui_->goToLineEdit->clear(); |
2932 | main_ui_->goToLineEdit->setFocus(); |
2933 | } |
2934 | }); |
2935 | |
2936 | connect(main_ui_->actionGoGoToLinkedPacket, &QAction::triggered, this, [this]() { |
2937 | QAction *gta = qobject_cast<QAction*>(sender()); |
2938 | if (!gta) return; |
2939 | |
2940 | bool ok = false; |
2941 | int packet_num = gta->data().toInt(&ok); |
2942 | if (!ok) return; |
2943 | |
2944 | packet_list_->goToPacket(packet_num); |
2945 | }); |
2946 | |
2947 | connect(main_ui_->actionGoNextPacket, &QAction::triggered, |
2948 | packet_list_, &PacketList::goNextPacket); |
2949 | |
2950 | connect(main_ui_->actionGoPreviousPacket, &QAction::triggered, |
2951 | packet_list_, &PacketList::goPreviousPacket); |
2952 | |
2953 | connect(main_ui_->actionGoFirstPacket, &QAction::triggered, |
2954 | packet_list_, &PacketList::goFirstPacket); |
2955 | |
2956 | connect(main_ui_->actionGoLastPacket, &QAction::triggered, |
2957 | packet_list_, &PacketList::goLastPacket); |
2958 | |
2959 | connect(main_ui_->actionGoNextConversationPacket, &QAction::triggered, this, |
2960 | [this]() { goToConversationFrame(true); }); |
2961 | |
2962 | connect(main_ui_->actionGoPreviousConversationPacket, &QAction::triggered, this, |
2963 | [this]() { goToConversationFrame(false); }); |
2964 | |
2965 | connect(main_ui_->actionGoNextHistoryPacket, &QAction::triggered, |
2966 | packet_list_, &PacketList::goNextHistoryPacket); |
2967 | |
2968 | connect(main_ui_->actionGoPreviousHistoryPacket, &QAction::triggered, |
2969 | packet_list_, &PacketList::goPreviousHistoryPacket); |
2970 | |
2971 | // triggered is whenever the user clicks the button; save that as |
2972 | // the new recent value |
2973 | connect(main_ui_->actionGoAutoScroll, &QAction::triggered, this, |
2974 | [](bool checked) { recent.capture_auto_scroll = checked; }); |
2975 | |
2976 | // toggled is whenever the value changes; if it changes programmatically |
2977 | // (e.g., the user scrolls upwards so we stop auto scrolling) change |
2978 | // whether the button is checked but don't save value to recent (it's |
2979 | // a temporary change) |
2980 | connect(main_ui_->actionGoAutoScroll, &QAction::toggled, this, |
2981 | [this](bool checked) { packet_list_->setVerticalAutoScroll(checked); }); |
2982 | } |
2983 | |
2984 | void WiresharkMainWindow::goToConversationFrame(bool go_next) { |
2985 | char *filter = NULL__null; |
2986 | dfilter_t *dfcode = NULL__null; |
2987 | bool found_packet = false; |
2988 | packet_info *pi = capture_file_.packetInfo(); |
2989 | |
2990 | if (!pi) { |
2991 | // No packet was selected, or multiple packets were selected. |
2992 | return; |
2993 | } |
2994 | |
2995 | /* Try to build a conversation |
2996 | * filter in the order TCP, UDP, IP, Ethernet and apply the |
2997 | * coloring */ |
2998 | filter = conversation_filter_from_packet(pi); |
2999 | if (filter == NULL__null) { |
3000 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, tr("Unable to build conversation filter.")); |
3001 | g_free(filter); |
3002 | return; |
3003 | } |
3004 | |
3005 | if (!dfilter_compile(filter, &dfcode, NULL)dfilter_compile_full(filter, &dfcode, __null, (1U << 1)|(1U << 2), __func__)) { |
3006 | /* The attempt failed; report an error. */ |
3007 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, tr("Error compiling filter for this conversation.")); |
3008 | g_free(filter); |
3009 | return; |
3010 | } |
3011 | |
3012 | found_packet = cf_find_packet_dfilter(capture_file_.capFile(), dfcode, go_next ? SD_FORWARD : SD_BACKWARD); |
3013 | |
3014 | if (!found_packet) { |
3015 | /* We didn't find a packet */ |
3016 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, tr("No previous/next packet in conversation.")); |
3017 | } |
3018 | |
3019 | dfilter_free(dfcode); |
3020 | g_free(filter); |
3021 | } |
3022 | |
3023 | // Capture Menu |
3024 | |
3025 | void WiresharkMainWindow::connectCaptureMenuActions() |
3026 | { |
3027 | #ifdef HAVE_LIBPCAP1 |
3028 | connect(main_ui_->actionCaptureOptions, &QAction::triggered, this, |
3029 | [this]() { showCaptureOptionsDialog(); }); |
3030 | #endif |
3031 | |
3032 | connect(main_ui_->actionCaptureStart, &QAction::triggered, this, |
3033 | [this]() { startCaptureTriggered(); }); |
3034 | |
3035 | connect(main_ui_->actionCaptureStop, &QAction::triggered, this, |
3036 | [this]() { stopCapture(); }); |
3037 | |
3038 | #ifdef HAVE_LIBPCAP1 |
3039 | connect(main_ui_->actionCaptureRestart, &QAction::triggered, this, [this]() { |
3040 | QString before_what(tr(" before restarting the capture")); |
3041 | cap_session_.capture_opts->restart = true; |
3042 | if (!testCaptureFileClose(before_what, Restart)) { |
3043 | return; |
3044 | } |
3045 | startCapture(QStringList()); |
3046 | }); |
3047 | #endif // HAVE_LIBPCAP |
3048 | |
3049 | connect(main_ui_->actionCaptureCaptureFilters, &QAction::triggered, this, [this]() { |
3050 | FilterDialog *capture_filter_dlg = new FilterDialog(window(), FilterDialog::CaptureFilter); |
3051 | capture_filter_dlg->setWindowModality(Qt::ApplicationModal); |
3052 | capture_filter_dlg->setAttribute(Qt::WA_DeleteOnClose); |
3053 | capture_filter_dlg->show(); |
3054 | }); |
3055 | |
3056 | #ifdef HAVE_LIBPCAP1 |
3057 | connect(main_ui_->actionCaptureRefreshInterfaces, &QAction::triggered, this, [this]() { |
3058 | main_ui_->actionCaptureRefreshInterfaces->setEnabled(false); |
3059 | mainApp->refreshLocalInterfaces(); |
3060 | main_ui_->actionCaptureRefreshInterfaces->setEnabled(true); |
3061 | }); |
3062 | #endif |
3063 | } |
3064 | |
3065 | void WiresharkMainWindow::showCaptureOptionsDialog() |
3066 | { |
3067 | #ifdef HAVE_LIBPCAP1 |
3068 | if (!capture_options_dialog_) { |
3069 | capture_options_dialog_ = new CaptureOptionsDialog(this); |
3070 | |
3071 | connect(capture_options_dialog_, &CaptureOptionsDialog::startCapture, this, [this]() { startCapture(); }); |
3072 | connect(capture_options_dialog_, &CaptureOptionsDialog::stopCapture, this, &WiresharkMainWindow::stopCapture); |
3073 | |
3074 | connect(capture_options_dialog_, &CaptureOptionsDialog::interfacesChanged, |
3075 | this->welcome_page_, &WelcomePage::interfaceSelected); |
3076 | connect(capture_options_dialog_, &CaptureOptionsDialog::interfacesChanged, |
3077 | this->welcome_page_->getInterfaceFrame(), &InterfaceFrame::updateSelectedInterfaces); |
3078 | connect(capture_options_dialog_, &CaptureOptionsDialog::interfaceListChanged, |
3079 | this->welcome_page_->getInterfaceFrame(), &InterfaceFrame::interfaceListChanged); |
3080 | connect(capture_options_dialog_, &CaptureOptionsDialog::captureFilterTextEdited, |
3081 | this->welcome_page_, &WelcomePage::setCaptureFilterText); |
3082 | // Propagate selection changes from main UI to dialog. |
3083 | connect(this->welcome_page_, &WelcomePage::interfacesChanged, |
3084 | capture_options_dialog_, &CaptureOptionsDialog::interfaceSelected); |
3085 | |
3086 | connect(capture_options_dialog_, &CaptureOptionsDialog::setFilterValid, |
3087 | this, &WiresharkMainWindow::startInterfaceCapture); |
3088 | |
3089 | connect(capture_options_dialog_, &CaptureOptionsDialog::showExtcapOptions, |
3090 | this, &WiresharkMainWindow::showExtcapOptionsDialog); |
3091 | } |
3092 | capture_options_dialog_->updateInterfaces(); |
3093 | |
3094 | if (capture_options_dialog_->isMinimized()) { |
3095 | capture_options_dialog_->showNormal(); |
3096 | } else { |
3097 | capture_options_dialog_->show(); |
3098 | } |
3099 | |
3100 | capture_options_dialog_->raise(); |
3101 | capture_options_dialog_->activateWindow(); |
3102 | #endif |
3103 | } |
3104 | |
3105 | void WiresharkMainWindow::startCaptureTriggered() |
3106 | { |
3107 | //#ifdef HAVE_AIRPCAP |
3108 | // airpcap_if_active = airpcap_if_selected; |
3109 | // if (airpcap_if_active) |
3110 | // airpcap_set_toolbar_start_capture(airpcap_if_active); |
3111 | //#endif |
3112 | |
3113 | // if (cap_open_w) { |
3114 | // /* |
3115 | // * There's an options dialog; get the values from it and close it. |
3116 | // */ |
3117 | // bool success; |
3118 | |
3119 | // /* Determine if "capture start" while building of the "capture options" window */ |
3120 | // /* is in progress. If so, ignore the "capture start. */ |
3121 | // /* XXX: Would it be better/cleaner for the "capture options" window code to */ |
3122 | // /* disable the capture start button temporarily ? */ |
3123 | // if (cap_open_complete == false) { |
3124 | // return; /* Building options window: ignore "capture start" */ |
3125 | // } |
3126 | // success = capture_dlg_prep(cap_open_w); |
3127 | // window_destroy(GTK_WIDGET(cap_open_w)); |
3128 | // if (!success) |
3129 | // return; /* error in options dialog */ |
3130 | // } |
3131 | |
3132 | #ifdef HAVE_LIBPCAP1 |
3133 | if (global_capture_opts.num_selected == 0) { |
3134 | QString err_msg = tr("No Interface Selected."); |
3135 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, err_msg); |
3136 | main_ui_->actionCaptureStart->setChecked(false); |
3137 | return; |
3138 | } |
3139 | |
3140 | /* XXX - will closing this remove a temporary file? */ |
3141 | QString before_what(tr(" before starting a new capture")); |
3142 | if (testCaptureFileClose(before_what)) { |
3143 | startCapture(QStringList()); |
3144 | } else { |
3145 | // simply clicking the button sets it to 'checked' even though we've |
3146 | // decided to do nothing, so undo that |
3147 | main_ui_->actionCaptureStart->setChecked(false); |
3148 | } |
3149 | #endif // HAVE_LIBPCAP |
3150 | } |
3151 | |
3152 | // Analyze Menu |
3153 | |
3154 | struct epan_uat; |
3155 | |
3156 | void WiresharkMainWindow::connectAnalyzeMenuActions() |
3157 | { |
3158 | connect(main_ui_->actionAnalyzeDisplayFilters, &QAction::triggered, this, [=]() { |
3159 | FilterDialog *display_filter_dlg = new FilterDialog(window(), FilterDialog::DisplayFilter); |
3160 | display_filter_dlg->setWindowModality(Qt::ApplicationModal); |
3161 | display_filter_dlg->setAttribute(Qt::WA_DeleteOnClose); |
3162 | display_filter_dlg->show(); |
3163 | }); |
3164 | |
3165 | connect(main_ui_->actionAnalyzeDisplayFilterMacros, &QAction::triggered, this, [=]() { |
3166 | FilterDialog *display_filter_dlg = new FilterDialog(window(), FilterDialog::DisplayMacro); |
3167 | display_filter_dlg->setWindowModality(Qt::ApplicationModal); |
3168 | display_filter_dlg->setAttribute(Qt::WA_DeleteOnClose); |
3169 | display_filter_dlg->show(); |
3170 | }); |
3171 | |
3172 | connect(main_ui_->actionDisplayFilterExpression, &QAction::triggered, this, [=]() { |
3173 | DisplayFilterExpressionDialog *dfe_dialog = new DisplayFilterExpressionDialog(this); |
3174 | |
3175 | connect(dfe_dialog, &DisplayFilterExpressionDialog::insertDisplayFilter, |
3176 | qobject_cast<SyntaxLineEdit *>(df_combo_box_->lineEdit()), &SyntaxLineEdit::insertFilter); |
3177 | |
3178 | dfe_dialog->show(); |
3179 | }); |
3180 | |
3181 | connect(main_ui_->actionAnalyzeApplyAsColumn, &QAction::triggered, this, &WiresharkMainWindow::applyFieldAsColumn); |
3182 | |
3183 | connect(main_ui_->actionAnalyzeEnabledProtocols, &QAction::triggered, this, [=]() { |
3184 | EnabledProtocolsDialog *enable_proto_dialog = new EnabledProtocolsDialog(this); |
3185 | connect(enable_proto_dialog, &EnabledProtocolsDialog::destroyed, mainApp, &MainApplication::flushAppSignals); |
3186 | |
3187 | enable_proto_dialog->setWindowModality(Qt::ApplicationModal); |
3188 | enable_proto_dialog->setAttribute(Qt::WA_DeleteOnClose); |
3189 | enable_proto_dialog->show(); |
3190 | }); |
3191 | |
3192 | connect(main_ui_->actionAnalyzeDecodeAs, &QAction::triggered, this, [=]() { |
3193 | QAction *da_action = qobject_cast<QAction*>(sender()); |
3194 | bool create_new = da_action && da_action->property("create_new").toBool(); |
3195 | |
3196 | DecodeAsDialog *da_dialog = new DecodeAsDialog(this, capture_file_.capFile(), create_new); |
3197 | connect(da_dialog, &DecodeAsDialog::destroyed, mainApp, &MainApplication::flushAppSignals); |
3198 | |
3199 | da_dialog->setWindowModality(Qt::ApplicationModal); |
3200 | da_dialog->setAttribute(Qt::WA_DeleteOnClose); |
3201 | da_dialog->show(); |
3202 | }); |
3203 | |
3204 | connect(main_ui_->actionAnalyzeReloadLuaPlugins, &QAction::triggered, this, &WiresharkMainWindow::reloadLuaPlugins); |
3205 | |
3206 | connect(main_ui_->actionAnalyzeShowPacketBytes, &QAction::triggered, this, [=]() { |
3207 | ShowPacketBytesDialog *spbd = new ShowPacketBytesDialog(*this, capture_file_); |
3208 | spbd->addCodecs(text_codec_map_); |
3209 | spbd->show(); |
3210 | }); |
3211 | |
3212 | connect(main_ui_->actionAnalyzeExpertInfo, &QAction::triggered, this, [=]() { |
3213 | statCommandExpertInfo(NULL__null, NULL__null); |
3214 | }); |
3215 | } |
3216 | |
3217 | void WiresharkMainWindow::filterMenuAboutToShow() |
3218 | { |
3219 | QMenu * menu = qobject_cast<QMenu *>(sender()); |
3220 | QString field_filter; |
3221 | |
3222 | if (capture_file_.capFile() && capture_file_.capFile()->finfo_selected) { |
3223 | char *tmp_field = proto_construct_match_selected_string(capture_file_.capFile()->finfo_selected, |
3224 | capture_file_.capFile()->edt); |
3225 | field_filter = QString(tmp_field); |
3226 | wmem_free(NULL__null, tmp_field); |
3227 | } |
3228 | bool enable = ! field_filter.isEmpty(); |
3229 | bool prepare = menu->objectName().compare("menuPrepareAFilter") == 0; |
3230 | |
3231 | menu->clear(); |
3232 | QActionGroup * group = FilterAction::createFilterGroup(field_filter, prepare, enable, menu); |
3233 | menu->addActions(group->actions()); |
3234 | } |
3235 | |
3236 | void WiresharkMainWindow::matchFieldFilter(FilterAction::Action action, FilterAction::ActionType filter_type) |
3237 | { |
3238 | QString field_filter; |
3239 | |
3240 | if (packet_list_->contextMenuActive() || packet_list_->hasFocus()) { |
3241 | field_filter = packet_list_->getFilterFromRowAndColumn(packet_list_->currentIndex()); |
3242 | } else if (capture_file_.capFile() && capture_file_.capFile()->finfo_selected) { |
3243 | char *tmp_field = proto_construct_match_selected_string(capture_file_.capFile()->finfo_selected, |
3244 | capture_file_.capFile()->edt); |
3245 | field_filter = QString(tmp_field); |
3246 | wmem_free(NULL__null, tmp_field); |
3247 | } |
3248 | |
3249 | if (field_filter.isEmpty()) { |
3250 | QString err = tr("No filter available. Try another %1.").arg(packet_list_->contextMenuActive() ? tr("column") : tr("item")); |
3251 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, err); |
3252 | return; |
3253 | } |
3254 | |
3255 | setDisplayFilter(field_filter, action, filter_type); |
3256 | } |
3257 | |
3258 | void WiresharkMainWindow::applyFieldAsColumn() |
3259 | { |
3260 | if (capture_file_.capFile() != 0 && capture_file_.capFile()->finfo_selected != 0) { |
3261 | const header_field_info *hfinfo = capture_file_.capFile()->finfo_selected->hfinfo; |
3262 | int col = column_prefs_has_custom(hfinfo->abbrev); |
3263 | if (col == -1) { |
3264 | insertColumn(hfinfo->name, hfinfo->abbrev); |
3265 | } else { |
3266 | QString status; |
3267 | if (QString(hfinfo->name) == get_column_title(col)) { |
3268 | status = tr("The \"%1\" column already exists.").arg(hfinfo->name); |
3269 | } else { |
3270 | status = tr("The \"%1\" column already exists as \"%2\".").arg(hfinfo->name).arg(get_column_title(col)); |
3271 | } |
3272 | mainApp->pushStatus(WiresharkApplication::TemporaryStatus, status); |
3273 | |
3274 | if (!get_column_visible(col)) { |
3275 | packet_list_->setColumnHidden(col, false); |
3276 | set_column_visible(col, true); |
3277 | prefs_main_write(); |
3278 | } |
3279 | } |
3280 | } |
3281 | } |
3282 | |
3283 | void WiresharkMainWindow::applyConversationFilter() |
3284 | { |
3285 | ConversationAction *conv_action = qobject_cast<ConversationAction*>(sender()); |
3286 | if (!conv_action) return; |
3287 | |
3288 | packet_info *pinfo = capture_file_.packetInfo(); |
3289 | if (!pinfo) return; |
3290 | |
3291 | QByteArray conv_filter = conv_action->filter(); |
3292 | if (conv_filter.isEmpty()) return; |
3293 | |
3294 | if (conv_action->isFilterValid(pinfo)) { |
3295 | |
3296 | df_combo_box_->lineEdit()->setText(conv_filter); |
3297 | df_combo_box_->applyDisplayFilter(); |
3298 | } |
3299 | } |
3300 | |
3301 | void WiresharkMainWindow::applyExportObject() |
3302 | { |
3303 | ExportObjectAction *export_action = qobject_cast<ExportObjectAction*>(sender()); |
3304 | if (!export_action) |
3305 | return; |
3306 | |
3307 | ExportObjectDialog* export_dialog = new ExportObjectDialog(*this, capture_file_, export_action->exportObject()); |
3308 | export_dialog->setWindowModality(Qt::ApplicationModal); |
3309 | export_dialog->setAttribute(Qt::WA_DeleteOnClose); |
3310 | export_dialog->show(); |
3311 | } |
3312 | |
3313 | void WiresharkMainWindow::openFollowStreamDialog(int proto_id, unsigned stream_num, unsigned sub_stream_num, bool use_stream_index) { |
3314 | FollowStreamDialog *fsd = new FollowStreamDialog(*this, capture_file_, proto_id); |
3315 | connect(fsd, &FollowStreamDialog::updateFilter, this, &WiresharkMainWindow::filterPackets); |
3316 | connect(fsd, &FollowStreamDialog::goToPacket, this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3317 | fsd->addCodecs(text_codec_map_); |
3318 | fsd->show(); |
3319 | if (use_stream_index) { |
3320 | // If a specific conversation was requested, then ignore any previous |
3321 | // display filters and display all related packets. |
3322 | fsd->follow("", true, stream_num, sub_stream_num); |
3323 | } else { |
3324 | fsd->follow(getFilter()); |
3325 | } |
3326 | } |
3327 | |
3328 | void WiresharkMainWindow::openFollowStreamDialog(int proto_id) { |
3329 | openFollowStreamDialog(proto_id, 0, 0, false); |
3330 | } |
3331 | |
3332 | void WiresharkMainWindow::openSCTPAllAssocsDialog() |
3333 | { |
3334 | SCTPAllAssocsDialog *sctp_dialog = new SCTPAllAssocsDialog(this, capture_file_.capFile()); |
3335 | connect(sctp_dialog, &SCTPAllAssocsDialog::filterPackets, this, &WiresharkMainWindow::filterPackets); |
3336 | connect(this, &WiresharkMainWindow::setCaptureFile, sctp_dialog, &SCTPAllAssocsDialog::setCaptureFile); |
3337 | sctp_dialog->fillTable(); |
3338 | |
3339 | if (sctp_dialog->isMinimized() == true) |
3340 | { |
3341 | sctp_dialog->showNormal(); |
3342 | } |
3343 | else |
3344 | { |
3345 | sctp_dialog->show(); |
3346 | } |
3347 | |
3348 | sctp_dialog->raise(); |
3349 | sctp_dialog->activateWindow(); |
3350 | } |
3351 | |
3352 | void WiresharkMainWindow::on_actionSCTPShowAllAssociations_triggered() |
3353 | { |
3354 | openSCTPAllAssocsDialog(); |
3355 | } |
3356 | |
3357 | void WiresharkMainWindow::on_actionSCTPAnalyseThisAssociation_triggered() |
3358 | { |
3359 | const sctp_assoc_info_t* assoc = SCTPAssocAnalyseDialog::findAssocForPacket(capture_file_.capFile()); |
3360 | if (!assoc) { |
3361 | return; |
3362 | } |
3363 | SCTPAssocAnalyseDialog *sctp_analyse = new SCTPAssocAnalyseDialog(this, assoc, capture_file_.capFile()); |
3364 | connect(sctp_analyse, &SCTPAssocAnalyseDialog::filterPackets, this, &WiresharkMainWindow::filterPackets); |
3365 | |
3366 | if (sctp_analyse->isMinimized() == true) |
3367 | { |
3368 | sctp_analyse->showNormal(); |
3369 | } |
3370 | else |
3371 | { |
3372 | sctp_analyse->show(); |
3373 | } |
3374 | |
3375 | sctp_analyse->raise(); |
3376 | sctp_analyse->activateWindow(); |
3377 | } |
3378 | |
3379 | void WiresharkMainWindow::on_actionSCTPFilterThisAssociation_triggered() |
3380 | { |
3381 | const sctp_assoc_info_t* assoc = SCTPAssocAnalyseDialog::findAssocForPacket(capture_file_.capFile()); |
3382 | if (assoc) { |
3383 | QString newFilter = QString("sctp.assoc_index==%1").arg(assoc->assoc_id); |
3384 | assoc = NULL__null; |
3385 | emit filterPackets(newFilter, false); |
3386 | } |
3387 | } |
3388 | |
3389 | // -z wlan,stat |
3390 | void WiresharkMainWindow::statCommandWlanStatistics(const char *arg, void *) |
3391 | { |
3392 | WlanStatisticsDialog *wlan_stats_dlg = new WlanStatisticsDialog(*this, capture_file_, arg); |
3393 | wlan_stats_dlg->show(); |
3394 | connect(wlan_stats_dlg, &WlanStatisticsDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
3395 | } |
3396 | |
3397 | // -z expert |
3398 | void WiresharkMainWindow::statCommandExpertInfo(const char *, void *) |
3399 | { |
3400 | const DisplayFilterEdit *df_edit = dynamic_cast<DisplayFilterEdit *>(df_combo_box_->lineEdit()); |
3401 | ExpertInfoDialog *expert_dialog = new ExpertInfoDialog(*this, capture_file_, df_edit->text()); |
3402 | |
3403 | connect(expert_dialog->getExpertInfoView(), &ExpertInfoTreeView::goToPacket, |
3404 | this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3405 | connect(expert_dialog, &ExpertInfoDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
3406 | |
3407 | expert_dialog->show(); |
3408 | } |
3409 | |
3410 | |
3411 | // Next / previous / first / last slots in packet_list |
3412 | |
3413 | // Statistics Menu |
3414 | |
3415 | void WiresharkMainWindow::connectStatisticsMenuActions() |
3416 | { |
3417 | connect(main_ui_->actionStatisticsCaptureFileProperties, &QAction::triggered, this, [=]() { |
3418 | CaptureFilePropertiesDialog *capture_file_properties_dialog = new CaptureFilePropertiesDialog(*this, capture_file_); |
3419 | connect(capture_file_properties_dialog, &CaptureFilePropertiesDialog::captureCommentChanged, |
3420 | this, &WiresharkMainWindow::updateForUnsavedChanges); |
3421 | capture_file_properties_dialog->show(); |
3422 | }); |
3423 | |
3424 | connect(main_ui_->actionStatisticsResolvedAddresses, &QAction::triggered, this, &WiresharkMainWindow::showResolvedAddressesDialog); |
3425 | |
3426 | connect(main_ui_->actionStatisticsProtocolHierarchy, &QAction::triggered, this, [=]() { |
3427 | ProtocolHierarchyDialog *phd = new ProtocolHierarchyDialog(*this, capture_file_); |
3428 | connect(phd, &ProtocolHierarchyDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
3429 | phd->show(); |
3430 | }); |
3431 | |
3432 | connect(main_ui_->actionStatisticsConversations, &QAction::triggered, this, &WiresharkMainWindow::showConversationsDialog); |
3433 | connect(main_ui_->actionStatisticsEndpoints, &QAction::triggered, this, &WiresharkMainWindow::showEndpointsDialog); |
3434 | |
3435 | connect(main_ui_->actionStatisticsPacketLengths, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("plen"); }); |
3436 | |
3437 | connect(main_ui_->actionStatisticsIOGraph, &QAction::triggered, this, [=]() { statCommandIOGraph(NULL__null, NULL__null); }); |
3438 | |
3439 | connect(main_ui_->actionStatisticsFlowGraph, &QAction::triggered, this, [=]() { |
3440 | SequenceDialog *sequence_dialog = new SequenceDialog(*this, capture_file_); |
3441 | sequence_dialog->show(); |
3442 | }); |
3443 | |
3444 | connect(main_ui_->actionStatisticsCollectd, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("collectd"); }); |
3445 | connect(main_ui_->actionStatisticsDNS, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("dns"); }); |
3446 | connect(main_ui_->actionStatisticsDNS_QR, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("dns_qr"); }); |
3447 | connect(main_ui_->actionStatisticsHART_IP, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("hart_ip"); }); |
3448 | connect(main_ui_->actionStatisticsHpfeeds, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("hpfeeds"); }); |
3449 | connect(main_ui_->actionStatisticsHTTP2, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("http2"); }); |
3450 | connect(main_ui_->actionStatisticsUdpMulticastStreams, &QAction::triggered, this, [=]() { statCommandMulticastStatistics(NULL__null, NULL__null); }); |
3451 | |
3452 | connect(main_ui_->actionStatistics29WestTopics_Advertisem*nts_by_Topic, &QAction::triggered, this, [=]() { |
3453 | openStatisticsTreeDialog("lbmr_topic_ads_topic"); |
3454 | }); |
3455 | |
3456 | connect(main_ui_->actionStatistics29WestTopics_Advertisem*nts_by_Source, &QAction::triggered, this, [=]() { |
3457 | openStatisticsTreeDialog("lbmr_topic_ads_source"); |
3458 | }); |
3459 | |
3460 | connect(main_ui_->actionStatistics29WestTopics_Advertisem*nts_by_Transport, &QAction::triggered, this, [=]() { |
3461 | openStatisticsTreeDialog("lbmr_topic_ads_transport"); |
3462 | }); |
3463 | |
3464 | connect(main_ui_->actionStatistics29WestTopics_Queries_by_Topic, &QAction::triggered, this, [=]() { |
3465 | openStatisticsTreeDialog("lbmr_topic_queries_topic"); |
3466 | }); |
3467 | |
3468 | connect(main_ui_->actionStatistics29WestTopics_Queries_by_Receiver, &QAction::triggered, this, [=]() { |
3469 | openStatisticsTreeDialog("lbmr_topic_queries_receiver"); |
3470 | }); |
3471 | |
3472 | connect(main_ui_->actionStatistics29WestTopics_Wildcard_Queries_by_Pattern, &QAction::triggered, this, [=]() { |
3473 | openStatisticsTreeDialog("lbmr_topic_queries_pattern"); |
3474 | }); |
3475 | |
3476 | connect(main_ui_->actionStatistics29WestTopics_Wildcard_Queries_by_Receiver, &QAction::triggered, this, [=]() { |
3477 | openStatisticsTreeDialog("lbmr_topic_queries_pattern_receiver"); |
3478 | }); |
3479 | |
3480 | connect(main_ui_->actionStatistics29WestQueues_Advertisem*nts_by_Queue, &QAction::triggered, this, [=]() { |
3481 | openStatisticsTreeDialog("lbmr_queue_ads_queue"); |
3482 | }); |
3483 | |
3484 | connect(main_ui_->actionStatistics29WestQueues_Advertisem*nts_by_Source, &QAction::triggered, this, [=]() { |
3485 | openStatisticsTreeDialog("lbmr_queue_ads_source"); |
3486 | }); |
3487 | |
3488 | connect(main_ui_->actionStatistics29WestQueues_Queries_by_Queue, &QAction::triggered, this, [=]() { |
3489 | openStatisticsTreeDialog("lbmr_queue_queries_queue"); |
3490 | }); |
3491 | |
3492 | connect(main_ui_->actionStatistics29WestQueues_Queries_by_Receiver, &QAction::triggered, this, [=]() { |
3493 | openStatisticsTreeDialog("lbmr_queue_queries_receiver"); |
3494 | }); |
3495 | |
3496 | connect(main_ui_->actionStatistics29WestUIM_Streams, &QAction::triggered, this, [=]() { |
3497 | LBMStreamDialog *stream_dialog = new LBMStreamDialog(this, capture_file_.capFile()); |
3498 | // connect(stream_dialog, &LBMStreamDialog::goToPacket, packet_list_, &PacketList::goToPacket); |
3499 | connect(this, &WiresharkMainWindow::setCaptureFile, stream_dialog, &LBMStreamDialog::setCaptureFile); |
3500 | stream_dialog->show(); |
3501 | }); |
3502 | |
3503 | connect(main_ui_->actionStatistics29WestLBTRM, &QAction::triggered, this, [=]() { |
3504 | LBMLBTRMTransportDialog * lbtrm_dialog = new LBMLBTRMTransportDialog(this, capture_file_.capFile()); |
3505 | connect(lbtrm_dialog, &LBMLBTRMTransportDialog::goToPacket, this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3506 | connect(this, &WiresharkMainWindow::setCaptureFile, lbtrm_dialog, &LBMLBTRMTransportDialog::setCaptureFile); |
3507 | lbtrm_dialog->show(); |
3508 | }); |
3509 | |
3510 | connect(main_ui_->actionStatistics29WestLBTRU, &QAction::triggered, this, [=]() { |
3511 | LBMLBTRUTransportDialog * lbtru_dialog = new LBMLBTRUTransportDialog(this, capture_file_.capFile()); |
3512 | connect(lbtru_dialog, &LBMLBTRUTransportDialog::goToPacket, this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3513 | connect(this, &WiresharkMainWindow::setCaptureFile, lbtru_dialog, &LBMLBTRUTransportDialog::setCaptureFile); |
3514 | lbtru_dialog->show(); |
3515 | }); |
3516 | |
3517 | connect(main_ui_->actionStatisticsTcpStreamStevens, &QAction::triggered, this, [=]() { openTcpStreamDialog(GRAPH_TSEQ_STEVENS); }); |
3518 | connect(main_ui_->actionStatisticsTcpStreamTcptrace, &QAction::triggered, this, [=]() { openTcpStreamDialog(GRAPH_TSEQ_TCPTRACE); }); |
3519 | connect(main_ui_->actionStatisticsTcpStreamThroughput, &QAction::triggered, this, [=]() { openTcpStreamDialog(GRAPH_THROUGHPUT); }); |
3520 | connect(main_ui_->actionStatisticsTcpStreamRoundTripTime, &QAction::triggered, this, [=]() { openTcpStreamDialog(GRAPH_RTT); }); |
3521 | connect(main_ui_->actionStatisticsTcpStreamWindowScaling, &QAction::triggered, this, [=]() { openTcpStreamDialog(GRAPH_WSCALE); }); |
3522 | |
3523 | connect(main_ui_->actionStatisticsANCP, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("ancp"); }); |
3524 | |
3525 | connect(main_ui_->actionStatisticsBACappInstanceId, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("bacapp_instanceid"); }); |
3526 | connect(main_ui_->actionStatisticsBACappIP, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("bacapp_ip"); }); |
3527 | connect(main_ui_->actionStatisticsBACappObjectId, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("bacapp_objectid"); }); |
3528 | connect(main_ui_->actionStatisticsBACappService, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("bacapp_service"); }); |
3529 | |
3530 | connect(main_ui_->actionStatisticsHTTPPacketCounter, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("http"); }); |
3531 | connect(main_ui_->actionStatisticsHTTPRequests, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("http_req"); }); |
3532 | connect(main_ui_->actionStatisticsHTTPLoadDistribution, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("http_srv"); }); |
3533 | connect(main_ui_->actionStatisticsHTTPRequestSequences, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("http_seq"); }); |
3534 | |
3535 | connect(main_ui_->actionStatisticsSametime, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("sametime"); }); |
3536 | |
3537 | connect(main_ui_->actionStatisticsSOMEIPmessages, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("someip_messages"); }); |
3538 | connect(main_ui_->actionStatisticsSOMEIPSDentries, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("someipsd_entries"); }); |
3539 | |
3540 | connect(main_ui_->actionStatisticsLTP, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("ltp"); }); |
3541 | } |
3542 | |
3543 | void WiresharkMainWindow::openTcpStreamDialog(int graph_type) |
3544 | { |
3545 | TCPStreamDialog *stream_dialog = new TCPStreamDialog(this, capture_file_.capFile(), (tcp_graph_type)graph_type); |
3546 | connect(stream_dialog, &TCPStreamDialog::goToPacket, this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3547 | connect(this, &WiresharkMainWindow::setCaptureFile, stream_dialog, &TCPStreamDialog::setCaptureFile); |
3548 | if (stream_dialog->result() == QDialog::Accepted) { |
3549 | stream_dialog->show(); |
3550 | } |
3551 | } |
3552 | |
3553 | // -z mcast,stat |
3554 | void WiresharkMainWindow::statCommandMulticastStatistics(const char *arg, void *) |
3555 | { |
3556 | MulticastStatisticsDialog *mcast_stats_dlg = new MulticastStatisticsDialog(*this, capture_file_, arg); |
3557 | connect(mcast_stats_dlg, &MulticastStatisticsDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
3558 | mcast_stats_dlg->show(); |
3559 | } |
3560 | |
3561 | void WiresharkMainWindow::openStatisticsTreeDialog(const char *abbr) |
3562 | { |
3563 | StatsTreeDialog *st_dialog = new StatsTreeDialog(*this, capture_file_, abbr); |
3564 | // connect(st_dialog, &StatsTreeDialog::goToPacket, packet_list_, &PacketList::goToPacket); |
3565 | st_dialog->show(); |
3566 | } |
3567 | |
3568 | // -z io,stat |
3569 | void WiresharkMainWindow::statCommandIOGraph(const char *, void *) |
3570 | { |
3571 | showIOGraphDialog(IOG_ITEM_UNIT_PACKETS, QString()); |
3572 | } |
3573 | |
3574 | void WiresharkMainWindow::showIOGraphDialog(io_graph_item_unit_t value_units, QString yfield) |
3575 | { |
3576 | const DisplayFilterEdit *df_edit = qobject_cast<DisplayFilterEdit *>(df_combo_box_->lineEdit()); |
3577 | IOGraphDialog *iog_dialog = nullptr; |
3578 | QString displayFilter; |
3579 | if (df_edit) |
3580 | displayFilter = df_edit->text(); |
3581 | |
3582 | if (!yfield.isEmpty()) { |
3583 | QList<IOGraphDialog *> iographdialogs = findChildren<IOGraphDialog *>(); |
3584 | // GeometryStateDialogs aren't parented on Linux and Windows |
3585 | // (see geometry_state_dialog.h), so we search for an |
3586 | // I/O Dialog in all the top level widgets. |
3587 | if (iographdialogs.isEmpty()) { |
3588 | foreach(QWidget *topLevelWidget, mainApp->topLevelWidgets())for (auto _container_3588 = QtPrivate::qMakeForeachContainer( mainApp->topLevelWidgets()); _container_3588.i != _container_3588 .e; ++_container_3588.i) if (QWidget *topLevelWidget = *_container_3588 .i; false) {} else { |
3589 | if (qobject_cast<IOGraphDialog*>(topLevelWidget)) { |
3590 | iographdialogs << qobject_cast<IOGraphDialog*>(topLevelWidget); |
3591 | } |
3592 | } |
3593 | } |
3594 | bool iog_found = false; |
3595 | foreach(iog_dialog, iographdialogs)for (auto _container_3595 = QtPrivate::qMakeForeachContainer( iographdialogs); _container_3595.i != _container_3595.e; ++_container_3595 .i) if (iog_dialog = *_container_3595.i; false) {} else { |
3596 | if (!iog_dialog->fileClosed()) { |
3597 | iog_found = true; |
3598 | iog_dialog->addGraph(true, displayFilter, value_units, yfield); |
3599 | break; |
3600 | } |
3601 | } |
3602 | if (!iog_found) { |
3603 | iog_dialog = nullptr; |
3604 | } |
3605 | } |
3606 | |
3607 | if (iog_dialog == nullptr) { |
3608 | iog_dialog = new IOGraphDialog(*this, capture_file_, displayFilter, value_units, yfield); |
3609 | connect(iog_dialog, &IOGraphDialog::goToPacket, this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3610 | connect(this, &WiresharkMainWindow::reloadFields, iog_dialog, &IOGraphDialog::reloadFields); |
3611 | } |
3612 | if (iog_dialog->isMinimized()) { |
3613 | iog_dialog->showNormal(); |
3614 | } else { |
3615 | iog_dialog->show(); |
3616 | } |
3617 | iog_dialog->raise(); |
3618 | iog_dialog->activateWindow(); |
3619 | } |
3620 | |
3621 | // Telephony Menu |
3622 | |
3623 | void WiresharkMainWindow::connectTelephonyMenuActions() |
3624 | { |
3625 | connect(main_ui_->actionTelephonyVoipCalls, &QAction::triggered, this, [=]() { |
3626 | VoipCallsDialog *dialog = VoipCallsDialog::openVoipCallsDialogVoip(*this, capture_file_, packet_list_); |
3627 | dialog->show(); |
3628 | }); |
3629 | |
3630 | connect(main_ui_->actionTelephonyIax2StreamAnalysis, &QAction::triggered, this, [=]() { |
3631 | Iax2AnalysisDialog *iax2_analysis_dialog = new Iax2AnalysisDialog(*this, capture_file_); |
3632 | connect(iax2_analysis_dialog, &Iax2AnalysisDialog::goToPacket, this, [=](int packet) { packet_list_->goToPacket(packet); }); |
3633 | iax2_analysis_dialog->show(); |
3634 | }); |
3635 | |
3636 | connect(main_ui_->actionTelephonyISUPMessages, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("isup_msg"); }); |
3637 | |
3638 | connect(main_ui_->actionTelephonyGsmMapSummary, &QAction::triggered, this, [=]() { |
3639 | GsmMapSummaryDialog *gms_dialog = new GsmMapSummaryDialog(*this, capture_file_); |
3640 | gms_dialog->show(); |
3641 | }); |
3642 | |
3643 | connect(main_ui_->actionTelephonyLteMacStatistics, &QAction::triggered, this, [=]() { statCommandLteMacStatistics(NULL__null, NULL__null); }); |
3644 | connect(main_ui_->actionTelephonyLteRlcGraph, &QAction::triggered, this, [=]() { |
3645 | // We don't yet know the channel. |
3646 | launchRLCGraph(false, RLC_RAT_LTE0, 0, 0, 0, 0, 0); |
3647 | }); |
3648 | connect(main_ui_->actionTelephonyLteRlcStatistics, &QAction::triggered, this, [=]() { statCommandLteRlcStatistics(NULL__null, NULL__null); }); |
3649 | |
3650 | connect(main_ui_->actionTelephonyMtp3Summary, &QAction::triggered, this, [=]() { |
3651 | Mtp3SummaryDialog *mtp3s_dialog = new Mtp3SummaryDialog(*this, capture_file_); |
3652 | mtp3s_dialog->show(); |
3653 | }); |
3654 | |
3655 | connect(main_ui_->actionTelephonyOsmuxPacketCounter, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("osmux"); }); |
3656 | |
3657 | connect(main_ui_->actionTelephonyRtpStreams, &QAction::triggered, this, &WiresharkMainWindow::openTelephonyRtpStreamsDialog); |
3658 | connect(main_ui_->actionTelephonyRtpStreamAnalysis, &QAction::triggered, this, &WiresharkMainWindow::openRtpStreamAnalysisDialog); |
3659 | connect(main_ui_->actionTelephonyRtpPlayer, &QAction::triggered, this, &WiresharkMainWindow::openRtpPlayerDialog); |
3660 | |
3661 | connect(main_ui_->actionTelephonyRTSPPacketCounter, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("rtsp"); }); |
3662 | |
3663 | connect(main_ui_->actionTelephonySMPPOperations, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("smpp_commands"); }); |
3664 | |
3665 | connect(main_ui_->actionTelephonyUCPMessages, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("ucp_messages"); }); |
3666 | |
3667 | connect(main_ui_->actionTelephonyF1APMessages, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("f1ap"); }); |
3668 | |
3669 | connect(main_ui_->actionTelephonyNGAPMessages, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("ngap"); }); |
3670 | |
3671 | connect(main_ui_->actionTelephonyE2APMessages, &QAction::triggered, this, [=]() { openStatisticsTreeDialog("e2ap"); }); |
3672 | |
3673 | connect(main_ui_->actionTelephonySipFlows, &QAction::triggered, this, [=]() { |
3674 | VoipCallsDialog *dialog = VoipCallsDialog::openVoipCallsDialogSip(*this, capture_file_, packet_list_); |
3675 | dialog->show(); |
3676 | }); |
3677 | } |
3678 | |
3679 | RtpPlayerDialog *WiresharkMainWindow::openTelephonyRtpPlayerDialog() |
3680 | { |
3681 | RtpPlayerDialog *dialog; |
3682 | |
3683 | #ifdef HAVE_LIBPCAP1 |
3684 | dialog = RtpPlayerDialog::openRtpPlayerDialog(*this, capture_file_, packet_list_, captureSession()->state != CAPTURE_STOPPED); |
3685 | #else |
3686 | dialog = RtpPlayerDialog::openRtpPlayerDialog(*this, capture_file_, packet_list_, false); |
3687 | #endif |
3688 | |
3689 | dialog->show(); |
3690 | |
3691 | return dialog; |
3692 | } |
3693 | |
3694 | RtpAnalysisDialog *WiresharkMainWindow::openTelephonyRtpAnalysisDialog() |
3695 | { |
3696 | RtpAnalysisDialog *dialog; |
3697 | |
3698 | dialog = RtpAnalysisDialog::openRtpAnalysisDialog(*this, capture_file_, packet_list_); |
3699 | dialog->show(); |
3700 | |
3701 | return dialog; |
3702 | } |
3703 | |
3704 | // -z mac-3gpp,stat |
3705 | void WiresharkMainWindow::statCommandLteMacStatistics(const char *arg, void *) |
3706 | { |
3707 | LteMacStatisticsDialog *lte_mac_stats_dlg = new LteMacStatisticsDialog(*this, capture_file_, arg); |
3708 | connect(lte_mac_stats_dlg, &LteMacStatisticsDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
3709 | lte_mac_stats_dlg->show(); |
3710 | } |
3711 | |
3712 | void WiresharkMainWindow::statCommandLteRlcStatistics(const char *arg, void *) |
3713 | { |
3714 | LteRlcStatisticsDialog *lte_rlc_stats_dlg = new LteRlcStatisticsDialog(*this, capture_file_, arg); |
3715 | connect(lte_rlc_stats_dlg, &LteRlcStatisticsDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
3716 | // N.B. It is necessary for the RLC Statistics window to launch the RLC graph in this way, to ensure |
3717 | // that the goToPacket() signal/slot connection gets set up... |
3718 | connect(lte_rlc_stats_dlg, &LteRlcStatisticsDialog::launchRLCGraph, this, &WiresharkMainWindow::launchRLCGraph); |
3719 | |
3720 | lte_rlc_stats_dlg->show(); |
3721 | } |
3722 | |
3723 | void WiresharkMainWindow::launchRLCGraph(bool channelKnown, |
3724 | uint8_t RAT, uint16_t ueid, uint8_t rlcMode, |
3725 | uint16_t channelType, uint16_t channelId, uint8_t direction) |
3726 | { |
3727 | LteRlcGraphDialog *lrg_dialog = new LteRlcGraphDialog(*this, capture_file_, channelKnown); |
3728 | connect(lrg_dialog, &LteRlcGraphDialog::goToPacket, this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3729 | // This is a bit messy, but wanted to hide these parameters from users of |
3730 | // on_actionTelephonyLteRlcGraph_triggered(). |
3731 | if (channelKnown) { |
3732 | lrg_dialog->setChannelInfo(RAT, ueid, rlcMode, channelType, channelId, direction); |
3733 | } |
3734 | lrg_dialog->show(); |
3735 | } |
3736 | |
3737 | RtpStreamDialog *WiresharkMainWindow::openTelephonyRtpStreamsDialog() |
3738 | { |
3739 | RtpStreamDialog *dialog = RtpStreamDialog::openRtpStreamDialog(*this, capture_file_, packet_list_); |
3740 | dialog->show(); |
3741 | |
3742 | return dialog; |
3743 | } |
3744 | |
3745 | void WiresharkMainWindow::openRtpStreamAnalysisDialog() |
3746 | { |
3747 | QVector<rtpstream_id_t *> stream_ids; |
3748 | QString err; |
3749 | |
3750 | if (QGuiApplication::keyboardModifiers().testFlag(Qt::ControlModifier)) { |
3751 | err = findRtpStreams(&stream_ids, true); |
3752 | } else { |
3753 | err = findRtpStreams(&stream_ids, false); |
3754 | } |
3755 | if (!err.isNull()) { |
3756 | QMessageBox::warning(this, tr("RTP packet search failed"), |
3757 | err, |
3758 | QMessageBox::Ok); |
3759 | } else { |
3760 | openTelephonyRtpAnalysisDialog()->addRtpStreams(stream_ids); |
3761 | } |
3762 | foreach(rtpstream_id_t *id, stream_ids)for (auto _container_3762 = QtPrivate::qMakeForeachContainer( stream_ids); _container_3762.i != _container_3762.e; ++_container_3762 .i) if (rtpstream_id_t *id = *_container_3762.i; false) {} else { |
3763 | rtpstream_id_free(id); |
3764 | g_free(id); |
3765 | } |
3766 | } |
3767 | |
3768 | void WiresharkMainWindow::openRtpPlayerDialog() |
3769 | { |
3770 | QVector<rtpstream_id_t *> stream_ids; |
3771 | QString err; |
3772 | |
3773 | if (QGuiApplication::keyboardModifiers().testFlag(Qt::ControlModifier)) { |
3774 | err = findRtpStreams(&stream_ids, true); |
3775 | } else { |
3776 | err = findRtpStreams(&stream_ids, false); |
3777 | } |
3778 | if (!err.isNull()) { |
3779 | QMessageBox::warning(this, tr("RTP packet search failed"), |
3780 | err, |
3781 | QMessageBox::Ok); |
3782 | #ifdef QT_MULTIMEDIA_LIB1 |
3783 | } else { |
3784 | openTelephonyRtpPlayerDialog()->addRtpStreams(stream_ids); |
3785 | #endif // QT_MULTIMEDIA_LIB |
3786 | } |
3787 | foreach(rtpstream_id_t *id, stream_ids)for (auto _container_3787 = QtPrivate::qMakeForeachContainer( stream_ids); _container_3787.i != _container_3787.e; ++_container_3787 .i) if (rtpstream_id_t *id = *_container_3787.i; false) {} else { |
3788 | rtpstream_id_free(id); |
3789 | g_free(id); |
3790 | } |
3791 | } |
3792 | |
3793 | // Wireless Menu |
3794 | |
3795 | void WiresharkMainWindow::connectWirelessMenuActions() |
3796 | { |
3797 | connect(main_ui_->actionBluetoothATT_Server_Attributes, &QAction::triggered, this, [=]() { |
3798 | BluetoothAttServerAttributesDialog *bluetooth_att_sever_attributes_dialog = new BluetoothAttServerAttributesDialog(*this, capture_file_); |
3799 | connect(bluetooth_att_sever_attributes_dialog, &BluetoothAttServerAttributesDialog::goToPacket, |
3800 | this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3801 | connect(bluetooth_att_sever_attributes_dialog, &BluetoothAttServerAttributesDialog::updateFilter, |
3802 | this, &WiresharkMainWindow::filterPackets); |
3803 | bluetooth_att_sever_attributes_dialog->show(); |
3804 | }); |
3805 | |
3806 | connect(main_ui_->actionBluetoothDevices, &QAction::triggered, this, [=]() { |
3807 | BluetoothDevicesDialog *bluetooth_devices_dialog = new BluetoothDevicesDialog(*this, capture_file_, packet_list_); |
3808 | connect(bluetooth_devices_dialog, &BluetoothDevicesDialog::goToPacket, this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3809 | connect(bluetooth_devices_dialog, &BluetoothDevicesDialog::updateFilter, |
3810 | this, &WiresharkMainWindow::filterPackets); |
3811 | bluetooth_devices_dialog->show(); |
3812 | }); |
3813 | |
3814 | connect(main_ui_->actionBluetoothHCI_Summary, &QAction::triggered, this, [=]() { |
3815 | BluetoothHciSummaryDialog *bluetooth_hci_summary_dialog = new BluetoothHciSummaryDialog(*this, capture_file_); |
3816 | connect(bluetooth_hci_summary_dialog, &BluetoothHciSummaryDialog::goToPacket, |
3817 | this, [=](int packet_num) {packet_list_->goToPacket(packet_num);}); |
3818 | connect(bluetooth_hci_summary_dialog, &BluetoothHciSummaryDialog::updateFilter, |
3819 | this, &WiresharkMainWindow::filterPackets); |
3820 | bluetooth_hci_summary_dialog->show(); |
3821 | }); |
3822 | |
3823 | connect(main_ui_->actionWirelessWlanStatistics, &QAction::triggered, this, [=]() { statCommandWlanStatistics(NULL__null, NULL__null); }); |
3824 | } |
3825 | |
3826 | // Tools Menu |
3827 | |
3828 | void WiresharkMainWindow::connectToolsMenuActions() |
3829 | { |
3830 | connect(main_ui_->actionToolsFirewallAclRules, &QAction::triggered, this, [=]() { |
3831 | FirewallRulesDialog *firewall_rules_dialog = new FirewallRulesDialog(*this, capture_file_); |
3832 | firewall_rules_dialog->show(); |
3833 | }); |
3834 | |
3835 | connect(main_ui_->actionToolsCredentials, &QAction::triggered, this, [=]() { |
3836 | CredentialsDialog *credentials_dialog = new CredentialsDialog(*this, capture_file_, packet_list_); |
3837 | credentials_dialog->show(); |
3838 | }); |
3839 | |
3840 | connect(main_ui_->actionToolsMacLookup, &QAction::triggered, this, [=]() { |
3841 | ManufDialog *manuf_dialog = new ManufDialog(*this, capture_file_); |
3842 | manuf_dialog->show(); |
3843 | }); |
3844 | |
3845 | connect(main_ui_->actionToolsTLSKeylog, &QAction::triggered, this, &WiresharkMainWindow::openTLSKeylogDialog); |
3846 | } |
3847 | |
3848 | // Help Menu |
3849 | void WiresharkMainWindow::connectHelpMenuActions() |
3850 | { |
3851 | |
3852 | connect(main_ui_->actionHelpAbout, &QAction::triggered, this, [=]() { |
3853 | AboutDialog *about_dialog = new AboutDialog(this); |
3854 | |
3855 | if (about_dialog->isMinimized() == true) |
3856 | { |
3857 | about_dialog->showNormal(); |
3858 | } |
3859 | else |
3860 | { |
3861 | about_dialog->show(); |
3862 | } |
3863 | |
3864 | about_dialog->raise(); |
3865 | about_dialog->activateWindow(); |
3866 | }); |
3867 | |
3868 | connect(main_ui_->actionHelpContents, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(HELP_CONTENT); }); |
3869 | connect(main_ui_->actionHelpMPWireshark, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_WIRESHARK); }); |
3870 | connect(main_ui_->actionHelpMPWireshark_Filter, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_WIRESHARK_FILTER); }); |
3871 | connect(main_ui_->actionHelpMPCapinfos, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_CAPINFOS); }); |
3872 | connect(main_ui_->actionHelpMPDumpcap, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_DUMPCAP); }); |
3873 | connect(main_ui_->actionHelpMPEditcap, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_EDITCAP); }); |
3874 | connect(main_ui_->actionHelpMPMergecap, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_MERGECAP); }); |
3875 | connect(main_ui_->actionHelpMPRawshark, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_RAWSHARK); }); |
3876 | connect(main_ui_->actionHelpMPReordercap, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_REORDERCAP); }); |
3877 | connect(main_ui_->actionHelpMPText2pcap, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_TEXT2PCAP); }); |
3878 | connect(main_ui_->actionHelpMPTShark, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_MAN_TSHARK); }); |
3879 | connect(main_ui_->actionHelpWebsite, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(ONLINEPAGE_HOME); }); |
3880 | connect(main_ui_->actionHelpFAQ, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(ONLINEPAGE_FAQ); }); |
3881 | connect(main_ui_->actionHelpAsk, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(ONLINEPAGE_ASK); }); |
3882 | connect(main_ui_->actionHelpDownloads, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(ONLINEPAGE_DOWNLOAD); }); |
3883 | connect(main_ui_->actionHelpWiki, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(ONLINEPAGE_WIKI); }); |
3884 | connect(main_ui_->actionHelpSampleCaptures, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(ONLINEPAGE_SAMPLE_FILES); }); |
3885 | connect(main_ui_->actionHelpReleaseNotes, &QAction::triggered, this, [=]() { mainApp->helpTopicAction(LOCALPAGE_RELEASE_NOTES); }); |
3886 | } |
3887 | |
3888 | #ifdef HAVE_SOFTWARE_UPDATE |
3889 | void WiresharkMainWindow::checkForUpdates() |
3890 | { |
3891 | software_update_check(); |
3892 | } |
3893 | #endif |
3894 | |
3895 | void WiresharkMainWindow::setPreviousFocus() { |
3896 | previous_focus_ = mainApp->focusWidget(); |
3897 | if (previous_focus_ != nullptr) { |
3898 | connect(previous_focus_, &QWidget::destroyed, this, &WiresharkMainWindow::resetPreviousFocus); |
3899 | } |
3900 | } |
3901 | |
3902 | void WiresharkMainWindow::resetPreviousFocus() { |
3903 | previous_focus_ = nullptr; |
3904 | } |
3905 | |
3906 | void WiresharkMainWindow::goToCancelClicked() |
3907 | { |
3908 | main_ui_->goToFrame->animatedHide(); |
3909 | if (previous_focus_) { |
3910 | disconnect(previous_focus_, &QWidget::destroyed, this, &WiresharkMainWindow::resetPreviousFocus); |
3911 | previous_focus_->setFocus(); |
3912 | resetPreviousFocus(); |
3913 | } |
3914 | } |
3915 | |
3916 | void WiresharkMainWindow::goToGoClicked() |
3917 | { |
3918 | gotoFrame(main_ui_->goToLineEdit->text().toInt()); |
3919 | |
3920 | goToCancelClicked(); |
3921 | } |
3922 | |
3923 | void WiresharkMainWindow::goToLineEditReturnPressed() |
3924 | { |
3925 | goToGoClicked(); |
3926 | } |
3927 | |
3928 | void WiresharkMainWindow::showResolvedAddressesDialog() |
3929 | { |
3930 | QString capFileName; |
3931 | wtap* wth = Q_NULLPTRnullptr; |
3932 | if (capture_file_.isValid()) |
3933 | { |
3934 | capFileName = capture_file_.capFile()->filename; |
3935 | wth = capture_file_.capFile()->provider.wth; |
3936 | } |
3937 | ResolvedAddressesDialog *resolved_addresses_dialog = |
3938 | new ResolvedAddressesDialog(this, capFileName, wth); |
3939 | resolved_addresses_dialog->show(); |
3940 | } |
3941 | |
3942 | void WiresharkMainWindow::showConversationsDialog() |
3943 | { |
3944 | ConversationDialog *conv_dialog = new ConversationDialog(*this, capture_file_); |
3945 | connect(conv_dialog, &ConversationDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
3946 | connect(conv_dialog, &ConversationDialog::openFollowStreamDialog, this, |
3947 | [=](int proto_id, unsigned stream_num, unsigned sub_stream_num) { |
3948 | openFollowStreamDialog(proto_id, stream_num, sub_stream_num); |
3949 | }); |
3950 | connect(conv_dialog, &ConversationDialog::openTcpStreamGraph, this, &WiresharkMainWindow::openTcpStreamDialog); |
3951 | conv_dialog->show(); |
3952 | } |
3953 | |
3954 | void WiresharkMainWindow::showEndpointsDialog() |
3955 | { |
3956 | EndpointDialog *endp_dialog = new EndpointDialog(*this, capture_file_); |
3957 | connect(endp_dialog, &EndpointDialog::filterAction, this, &WiresharkMainWindow::filterAction); |
3958 | connect(endp_dialog, &EndpointDialog::openFollowStreamDialog, this, |
3959 | [=](int proto_id) {openFollowStreamDialog(proto_id); |
3960 | }); |
3961 | connect(endp_dialog, &EndpointDialog::openTcpStreamGraph, this, &WiresharkMainWindow::openTcpStreamDialog); |
3962 | endp_dialog->show(); |
3963 | } |
3964 | |
3965 | void WiresharkMainWindow::externalMenuItemTriggered() |
3966 | { |
3967 | QAction * triggerAction = NULL__null; |
3968 | QVariant v; |
3969 | ext_menubar_t * entry = NULL__null; |
3970 | |
3971 | if (QObject::sender()) { |
3972 | triggerAction = (QAction *)QObject::sender(); |
3973 | v = triggerAction->data(); |
3974 | |
3975 | if (v.canConvert<void *>()) { |
3976 | entry = (ext_menubar_t *)v.value<void *>(); |
3977 | |
3978 | if (entry->type == EXT_MENUBAR_ITEM) { |
3979 | entry->callback(EXT_MENUBAR_QT_GUI, (void *)((void *)main_ui_), entry->user_data); |
3980 | } else { |
3981 | QDesktopServices::openUrl(QUrl(QString((char *)entry->user_data))); |
3982 | } |
3983 | } |
3984 | } |
3985 | } |
3986 | |
3987 | void WiresharkMainWindow::extcap_options_finished(int result) |
3988 | { |
3989 | if (result == QDialog::Accepted) { |
3990 | QString before_what(tr(" before starting a new capture")); |
3991 | if (testCaptureFileClose(before_what)) { |
3992 | startCapture(QStringList()); |
3993 | } |
3994 | } |
3995 | this->welcome_page_->getInterfaceFrame()->interfaceListChanged(); |
3996 | } |
3997 | |
3998 | void WiresharkMainWindow::showExtcapOptionsDialog(QString &device_name, bool startCaptureOnClose) |
3999 | { |
4000 | ExtcapOptionsDialog * extcap_options_dialog = ExtcapOptionsDialog::createForDevice(device_name, startCaptureOnClose, this); |
4001 | /* The dialog returns null, if the given device name is not a valid extcap device */ |
4002 | if (extcap_options_dialog) { |
4003 | extcap_options_dialog->setModal(true); |
4004 | extcap_options_dialog->setAttribute(Qt::WA_DeleteOnClose); |
4005 | connect(extcap_options_dialog, &ExtcapOptionsDialog::finished, this, &WiresharkMainWindow::extcap_options_finished); |
4006 | #ifdef HAVE_LIBPCAP1 |
4007 | if (capture_options_dialog_) { |
4008 | /* Allow capture options dialog to close */ |
4009 | connect(extcap_options_dialog, &ExtcapOptionsDialog::accepted, capture_options_dialog_, &CaptureOptionsDialog::accept); |
4010 | } |
4011 | #endif |
4012 | extcap_options_dialog->show(); |
4013 | } |
4014 | } |
4015 | |
4016 | void WiresharkMainWindow::on_actionContextWikiProtocolPage_triggered() |
4017 | { |
4018 | QAction *wa = qobject_cast<QAction*>(sender()); |
4019 | if (!wa) return; |
4020 | |
4021 | bool ok = false; |
4022 | int field_id = wa->data().toInt(&ok); |
4023 | if (!ok) return; |
4024 | |
4025 | const QString proto_abbrev = proto_registrar_get_abbrev(field_id); |
4026 | |
4027 | int ret = QMessageBox::question(this, mainApp->windowTitleString(tr("Wiki Page for %1").arg(proto_abbrev)), |
4028 | tr("<p>The Wireshark Wiki is maintained by the community.</p>" |
4029 | "<p>The page you are about to load might be wonderful, " |
4030 | "incomplete, wrong, or nonexistent.</p>" |
4031 | "<p>Proceed to the wiki?</p>"), |
4032 | QMessageBox::Yes | QMessageBox::No, QMessageBox::Yes); |
4033 | |
4034 | if (ret != QMessageBox::Yes) return; |
4035 | |
4036 | QUrl wiki_url = QString(WS_WIKI_URL("Protocols/%1")"https://wiki.wireshark.org" "/" "Protocols/%1").arg(proto_abbrev); |
4037 | QDesktopServices::openUrl(wiki_url); |
4038 | } |
4039 | |
4040 | void WiresharkMainWindow::on_actionContextFilterFieldReference_triggered() |
4041 | { |
4042 | QAction *wa = qobject_cast<QAction*>(sender()); |
4043 | if (!wa) return; |
4044 | |
4045 | bool ok = false; |
4046 | int field_id = wa->data().toInt(&ok); |
4047 | if (!ok) return; |
4048 | |
4049 | const QString proto_abbrev = proto_registrar_get_abbrev(field_id); |
4050 | |
4051 | QUrl dfref_url = QString(WS_DOCS_URL"https://www.wireshark.org/docs/" "/dfref/%1/%2") |
4052 | .arg(proto_abbrev[0]) |
4053 | .arg(proto_abbrev); |
4054 | QDesktopServices::openUrl(dfref_url); |
4055 | } |
4056 | |
4057 | void WiresharkMainWindow::activatePluginIFToolbar(bool) |
4058 | { |
4059 | QAction *sendingAction = dynamic_cast<QAction *>(sender()); |
4060 | if (!sendingAction || !sendingAction->data().isValid()) |
4061 | return; |
4062 | |
4063 | ext_toolbar_t *toolbar = VariantPointer<ext_toolbar_t>::asPtr(sendingAction->data()); |
4064 | |
4065 | QList<QToolBar *> toolbars = findChildren<QToolBar *>(); |
4066 | foreach(QToolBar *bar, toolbars)for (auto _container_4066 = QtPrivate::qMakeForeachContainer( toolbars); _container_4066.i != _container_4066.e; ++_container_4066 .i) if (QToolBar *bar = *_container_4066.i; false) {} else { |
4067 | AdditionalToolBar *iftoolbar = dynamic_cast<AdditionalToolBar *>(bar); |
4068 | if (iftoolbar && iftoolbar->menuName().compare(toolbar->name) == 0) { |
4069 | if (iftoolbar->isVisible()) { |
4070 | iftoolbar->setVisible(false); |
4071 | sendingAction->setChecked(true); |
4072 | } else { |
4073 | iftoolbar->setVisible(true); |
4074 | sendingAction->setChecked(true); |
4075 | } |
4076 | } |
4077 | } |
4078 | } |
4079 | |
4080 | void WiresharkMainWindow::rtpPlayerDialogReplaceRtpStreams(QVector<rtpstream_id_t *> stream_ids _U___attribute__((unused))) |
4081 | { |
4082 | #ifdef QT_MULTIMEDIA_LIB1 |
4083 | openTelephonyRtpPlayerDialog()->replaceRtpStreams(stream_ids); |
4084 | #endif |
4085 | } |
4086 | |
4087 | void WiresharkMainWindow::rtpPlayerDialogAddRtpStreams(QVector<rtpstream_id_t *> stream_ids _U___attribute__((unused))) |
4088 | { |
4089 | #ifdef QT_MULTIMEDIA_LIB1 |
4090 | openTelephonyRtpPlayerDialog()->addRtpStreams(stream_ids); |
4091 | #endif |
4092 | } |
4093 | |
4094 | void WiresharkMainWindow::rtpPlayerDialogRemoveRtpStreams(QVector<rtpstream_id_t *> stream_ids _U___attribute__((unused))) |
4095 | { |
4096 | #ifdef QT_MULTIMEDIA_LIB1 |
4097 | openTelephonyRtpPlayerDialog()->removeRtpStreams(stream_ids); |
4098 | #endif |
4099 | } |
4100 | |
4101 | void WiresharkMainWindow::rtpAnalysisDialogReplaceRtpStreams(QVector<rtpstream_id_t *> stream_ids) |
4102 | { |
4103 | openTelephonyRtpAnalysisDialog()->replaceRtpStreams(stream_ids); |
4104 | } |
4105 | |
4106 | void WiresharkMainWindow::rtpAnalysisDialogAddRtpStreams(QVector<rtpstream_id_t *> stream_ids) |
4107 | { |
4108 | openTelephonyRtpAnalysisDialog()->addRtpStreams(stream_ids); |
4109 | } |
4110 | |
4111 | void WiresharkMainWindow::rtpAnalysisDialogRemoveRtpStreams(QVector<rtpstream_id_t *> stream_ids) |
4112 | { |
4113 | openTelephonyRtpAnalysisDialog()->removeRtpStreams(stream_ids); |
4114 | } |
4115 | |
4116 | void WiresharkMainWindow::rtpStreamsDialogSelectRtpStreams(QVector<rtpstream_id_t *> stream_ids) |
4117 | { |
4118 | openTelephonyRtpStreamsDialog()->selectRtpStream(stream_ids); |
4119 | } |
4120 | |
4121 | void WiresharkMainWindow::rtpStreamsDialogDeselectRtpStreams(QVector<rtpstream_id_t *> stream_ids) |
4122 | { |
4123 | openTelephonyRtpStreamsDialog()->deselectRtpStream(stream_ids); |
4124 | } |
4125 | |
4126 | #ifdef _MSC_VER |
4127 | #pragma warning(pop) |
4128 | #endif |