1 /* lbm_lbtrm_transport_dialog.cpp
3 * Copyright (c) 2005-2014 Informatica Corporation. All Rights Reserved.
5 * Wireshark - Network traffic analyzer
6 * By Gerald Combs <gerald@wireshark.org>
7 * Copyright 1998 Gerald Combs
9 * SPDX-License-Identifier: GPL-2.0-or-later
12 #include "lbm_lbtrm_transport_dialog.h"
13 #include <ui_lbm_lbtrm_transport_dialog.h>
17 #include <ui/qt/utils/qt_ui_utils.h>
18 #include "main_application.h"
22 #include <QMessageBox>
23 #include <QTreeWidget>
24 #include <QTreeWidgetItemIterator>
27 #include <epan/packet_info.h>
29 #include <epan/to_str.h>
30 #include <epan/dissectors/packet-lbm.h>
31 #include <wsutil/nstime.h>
35 static const int Source_AddressTransport_Column
= 0;
36 static const int Source_DataFrames_Column
= 1;
37 static const int Source_DataBytes_Column
= 2;
38 static const int Source_DataFramesBytes_Column
= 3;
39 static const int Source_DataRate_Column
= 4;
40 static const int Source_RXDataFrames_Column
= 5;
41 static const int Source_RXDataBytes_Column
= 6;
42 static const int Source_RXDataFramesBytes_Column
= 7;
43 static const int Source_RXDataRate_Column
= 8;
44 static const int Source_NCFFrames_Column
= 9;
45 static const int Source_NCFCount_Column
= 10;
46 static const int Source_NCFBytes_Column
= 11;
47 static const int Source_NCFFramesBytes_Column
= 12;
48 static const int Source_NCFCountBytes_Column
= 13;
49 static const int Source_NCFFramesCount_Column
= 14;
50 static const int Source_NCFFramesCountBytes_Column
= 15;
51 static const int Source_NCFRate_Column
= 16;
52 static const int Source_SMFrames_Column
= 17;
53 static const int Source_SMBytes_Column
= 18;
54 static const int Source_SMFramesBytes_Column
= 19;
55 static const int Source_SMRate_Column
= 20;
57 static const int Receiver_AddressTransport_Column
= 0;
58 static const int Receiver_NAKFrames_Column
= 1;
59 static const int Receiver_NAKCount_Column
= 2;
60 static const int Receiver_NAKBytes_Column
= 3;
61 static const int Receiver_NAKRate_Column
= 4;
63 static const int Detail_SQN_Column
= 0;
64 static const int Detail_Count_Column
= 1;
65 static const int Detail_Frame_Column
= 2;
67 static const double OneKilobit
= 1000.0;
68 static const double OneMegabit
= OneKilobit
* OneKilobit
;
69 static const double OneGigabit
= OneMegabit
* OneKilobit
;
72 static QString
format_rate(const nstime_t
& elapsed
, uint64_t bytes
)
78 if (((elapsed
.secs
== 0) && (elapsed
.nsecs
== 0)) || (bytes
== 0))
80 return (QStringLiteral("0"));
83 elapsed_sec
= elapsed
.secs
+ (((double)elapsed
.nsecs
) / 1000000000.0);
84 rate
= ((double)(bytes
* 8)) / elapsed_sec
;
86 // Currently rate is in bps
87 if (rate
>= OneGigabit
)
90 result
= QStringLiteral("%1G").arg(rate
, 0, 'f', 2);
92 else if (rate
>= OneMegabit
)
95 result
= QStringLiteral("%1M").arg(rate
, 0, 'f', 2);
97 else if (rate
>= OneKilobit
)
100 result
= QStringLiteral("%1K").arg(rate
, 0, 'f', 2);
104 result
= QStringLiteral("%1").arg(rate
, 0, 'f', 2);
110 // LBMLBTRMFrameEntry, LBMLBTRMSQNEntry, LBMLBTRMNCFReasonEntry, LBMLBTRMNCFSQNEntry, LBMLBTRMSourceTransportEntry, LBMLBTRMSourceEntry,
111 // LBMLBTRMReceiverTransportEntry, and LBMLBTRMReceiverEntry are all derived from a QTreeWidgetItem. Each instantiation can exist
112 // in two places: in a QTreeWidget, and in a containing QMap.
115 // - LBMLBTRMTransportDialogInfo contains a QMap of the sources (LBMLBTRMSourceEntry) and receivers (LBMLBTRMReceiverEntry)
116 // - A source (LBMLBTRMSourceEntry) contains a QMap of the source transports originating from it (LBMLBTRMSourceTransportEntry)
117 // - A source transport (LBMLBTRMSourceTransportEntry) contains QMaps of data, RX data, and SM SQNs (LBMLBTRMSQNEntry) and NCF SQNs
118 // (LBMLBTRMNCFSQNEntry)
119 // - A data SQN (LBMLBTRMSQNEntry) contains a QMap of the frames (LBMLBTRMFrameEntry) in which that SQN appears
121 // Not all of the entries actually appear in a QTreeWidget at one time. For example, in the source details, if no specific source
122 // transport is selected, nothing is in the source details tree. If Data SQNs is selected, then those details appear in the source
123 // details tree. Switching to RX Data SQNs removes whatever is currently in the source details tree, and adds the RX details for
124 // the selected transport.
126 // The actual owner of one of the above QTreeWidgetItem-derived items is the QMap container in its parent. The item is "loaned" to
127 // the QTreeWidget for display.
129 // All of this is to explain why
130 // 1) we are frequently adding things to a QTreeWidget
131 // 2) things are removed (takeTopLevelItem) from a QTreeWidget
132 // 3) destruction involves removing all items from all QTreeWidgets (rather than letting QTreeWidget delete them)
133 // 4) the destructor for each item has the form
134 // <for each QMap container>
135 // for (XXXMapIterator it = m_xxx.begin(); it != m_xxx.end(); it++)
140 // The for-loop calls the destructor for each item, while the clear() cleans up the space used by the QMap itself.
143 class LBMLBTRMFrameEntry
: public QTreeWidgetItem
146 LBMLBTRMFrameEntry(uint32_t frame
);
147 virtual ~LBMLBTRMFrameEntry(void) { }
148 uint32_t getFrame(void) { return (m_frame
); }
154 LBMLBTRMFrameEntry::LBMLBTRMFrameEntry(uint32_t frame
) :
158 setText(Detail_SQN_Column
, QStringLiteral(" "));
159 setText(Detail_Count_Column
, QStringLiteral(" "));
160 setText(Detail_Frame_Column
, QStringLiteral("%1").arg(m_frame
));
163 typedef QMap
<uint32_t, LBMLBTRMFrameEntry
*> LBMLBTRMFrameMap
;
164 typedef QMap
<uint32_t, LBMLBTRMFrameEntry
*>::iterator LBMLBTRMFrameMapIterator
;
166 // A SQN (SeQuence Number) entry
167 class LBMLBTRMSQNEntry
: public QTreeWidgetItem
170 LBMLBTRMSQNEntry(uint32_t sqn
);
171 virtual ~LBMLBTRMSQNEntry(void);
172 void processFrame(uint32_t frame
);
175 LBMLBTRMSQNEntry(void);
178 LBMLBTRMFrameMap m_frames
;
181 LBMLBTRMSQNEntry::LBMLBTRMSQNEntry(uint32_t sqn
) :
187 setText(Detail_SQN_Column
, QStringLiteral("%1").arg(m_sqn
));
188 setTextAlignment(Detail_SQN_Column
, Qt::AlignRight
);
189 setText(Detail_Count_Column
, QStringLiteral("%1").arg(m_count
));
190 setTextAlignment(Detail_Count_Column
, Qt::AlignRight
);
191 setText(Detail_Frame_Column
, QStringLiteral(" "));
194 LBMLBTRMSQNEntry::~LBMLBTRMSQNEntry(void)
196 for (LBMLBTRMFrameMapIterator it
= m_frames
.begin(); it
!= m_frames
.end(); ++it
)
203 void LBMLBTRMSQNEntry::processFrame(uint32_t frame
)
205 LBMLBTRMFrameMapIterator it
;
207 it
= m_frames
.find(frame
);
208 if (m_frames
.end() == it
)
210 LBMLBTRMFrameEntry
* entry
= new LBMLBTRMFrameEntry(frame
);
211 m_frames
.insert(frame
, entry
);
213 sortChildren(Detail_Frame_Column
, Qt::AscendingOrder
);
216 setText(Detail_Count_Column
, QStringLiteral("%1").arg(m_count
));
217 setTextAlignment(Detail_Count_Column
, Qt::AlignRight
);
220 // An NCF (Nak ConFirmation) Reason entry
221 class LBMLBTRMNCFReasonEntry
: public QTreeWidgetItem
224 LBMLBTRMNCFReasonEntry(uint8_t reason
);
225 virtual ~LBMLBTRMNCFReasonEntry(void);
226 void processFrame(uint32_t frame
);
229 LBMLBTRMNCFReasonEntry(void);
231 QString m_reason_string
;
233 LBMLBTRMFrameMap m_frames
;
236 LBMLBTRMNCFReasonEntry::LBMLBTRMNCFReasonEntry(uint8_t reason
) :
245 case LBTRM_NCF_REASON_NO_RETRY
:
246 m_reason_string
= "No Retry";
248 case LBTRM_NCF_REASON_IGNORED
:
249 m_reason_string
= "Ignored";
251 case LBTRM_NCF_REASON_RX_DELAY
:
252 m_reason_string
= "Retransmit Delay";
254 case LBTRM_NCF_REASON_SHED
:
255 m_reason_string
= "Shed";
258 m_reason_string
= QStringLiteral("Unknown (%1)").arg(m_reason
);
261 setText(Detail_SQN_Column
, m_reason_string
);
262 setText(Detail_Count_Column
, QStringLiteral("%1").arg(m_count
));
263 setTextAlignment(Detail_Count_Column
, Qt::AlignRight
);
264 setText(Detail_Frame_Column
, QStringLiteral(" "));
267 LBMLBTRMNCFReasonEntry::~LBMLBTRMNCFReasonEntry(void)
269 for (LBMLBTRMFrameMapIterator it
= m_frames
.begin(); it
!= m_frames
.end(); ++it
)
276 void LBMLBTRMNCFReasonEntry::processFrame(uint32_t frame
)
278 LBMLBTRMFrameMapIterator it
;
280 it
= m_frames
.find(frame
);
281 if (m_frames
.end() == it
)
283 LBMLBTRMFrameEntry
* entry
= new LBMLBTRMFrameEntry(frame
);
284 m_frames
.insert(frame
, entry
);
286 sortChildren(Detail_Frame_Column
, Qt::AscendingOrder
);
289 setText(Detail_Count_Column
, QStringLiteral("%1").arg(m_count
));
290 setTextAlignment(Detail_Count_Column
, Qt::AlignRight
);
293 typedef QMap
<uint32_t, LBMLBTRMNCFReasonEntry
*> LBMLBTRMNCFReasonMap
;
294 typedef QMap
<uint32_t, LBMLBTRMNCFReasonEntry
*>::iterator LBMLBTRMNCFReasonMapIterator
;
297 class LBMLBTRMNCFSQNEntry
: public QTreeWidgetItem
300 LBMLBTRMNCFSQNEntry(uint32_t sqn
);
301 virtual ~LBMLBTRMNCFSQNEntry(void);
302 void processFrame(uint8_t reason
, uint32_t frame
);
305 LBMLBTRMNCFSQNEntry(void);
308 LBMLBTRMNCFReasonMap m_reasons
;
311 LBMLBTRMNCFSQNEntry::LBMLBTRMNCFSQNEntry(uint32_t sqn
) :
317 setText(Detail_SQN_Column
, QStringLiteral("%1").arg(m_sqn
));
318 setTextAlignment(Detail_SQN_Column
, Qt::AlignRight
);
319 setText(Detail_Count_Column
, QStringLiteral("%1").arg(m_count
));
320 setTextAlignment(Detail_Count_Column
, Qt::AlignRight
);
321 setText(Detail_Frame_Column
, QStringLiteral(" "));
324 LBMLBTRMNCFSQNEntry::~LBMLBTRMNCFSQNEntry(void)
326 for (LBMLBTRMNCFReasonMapIterator it
= m_reasons
.begin(); it
!= m_reasons
.end(); ++it
)
333 void LBMLBTRMNCFSQNEntry::processFrame(uint8_t reason
, uint32_t frame
)
335 LBMLBTRMNCFReasonMapIterator it
;
336 LBMLBTRMNCFReasonEntry
* entry
= NULL
;
338 it
= m_reasons
.find(reason
);
339 if (m_reasons
.end() == it
)
341 entry
= new LBMLBTRMNCFReasonEntry(reason
);
342 m_reasons
.insert(reason
, entry
);
344 sortChildren(Detail_Frame_Column
, Qt::AscendingOrder
);
351 setText(Detail_Count_Column
, QStringLiteral("%1").arg(m_count
));
352 setTextAlignment(Detail_Count_Column
, Qt::AlignRight
);
353 entry
->processFrame(frame
);
356 typedef QMap
<uint32_t, LBMLBTRMSQNEntry
*> LBMLBTRMSQNMap
;
357 typedef QMap
<uint32_t, LBMLBTRMSQNEntry
*>::iterator LBMLBTRMSQNMapIterator
;
358 typedef QMap
<uint32_t, LBMLBTRMNCFSQNEntry
*> LBMLBTRMNCFSQNMap
;
359 typedef QMap
<uint32_t, LBMLBTRMNCFSQNEntry
*>::iterator LBMLBTRMNCFSQNMapIterator
;
361 // A source transport entry
362 class LBMLBTRMSourceTransportEntry
: public QTreeWidgetItem
364 friend class LBMLBTRMTransportDialog
;
367 LBMLBTRMSourceTransportEntry(const QString
& transport
);
368 virtual ~LBMLBTRMSourceTransportEntry(void);
369 void processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
);
376 uint64_t m_data_frames
;
377 uint64_t m_data_bytes
;
378 uint64_t m_rx_data_frames
;
379 uint64_t m_rx_data_bytes
;
380 uint64_t m_ncf_frames
;
381 uint64_t m_ncf_count
;
382 uint64_t m_ncf_bytes
;
383 uint64_t m_sm_frames
;
385 nstime_t m_first_frame_timestamp
;
386 bool m_first_frame_timestamp_valid
;
387 nstime_t m_last_frame_timestamp
;
390 LBMLBTRMSQNMap m_data_sqns
;
391 LBMLBTRMSQNMap m_rx_data_sqns
;
392 LBMLBTRMNCFSQNMap m_ncf_sqns
;
393 LBMLBTRMSQNMap m_sm_sqns
;
396 LBMLBTRMSourceTransportEntry::LBMLBTRMSourceTransportEntry(const QString
& transport
) :
398 m_transport(transport
),
408 m_first_frame_timestamp_valid(false),
414 m_first_frame_timestamp
.secs
= 0;
415 m_first_frame_timestamp
.nsecs
= 0;
416 m_last_frame_timestamp
.secs
= 0;
417 m_last_frame_timestamp
.nsecs
= 0;
418 setText(Source_AddressTransport_Column
, m_transport
);
421 LBMLBTRMSourceTransportEntry::~LBMLBTRMSourceTransportEntry(void)
423 for (LBMLBTRMSQNMapIterator it
= m_data_sqns
.begin(); it
!= m_data_sqns
.end(); ++it
)
429 for (LBMLBTRMSQNMapIterator it
= m_rx_data_sqns
.begin(); it
!= m_rx_data_sqns
.end(); ++it
)
433 m_rx_data_sqns
.clear();
435 for (LBMLBTRMNCFSQNMapIterator it
= m_ncf_sqns
.begin(); it
!= m_ncf_sqns
.end(); ++it
)
441 for (LBMLBTRMSQNMapIterator it
= m_sm_sqns
.begin(); it
!= m_sm_sqns
.end(); ++it
)
448 void LBMLBTRMSourceTransportEntry::processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
)
450 if (m_first_frame_timestamp_valid
)
452 if (nstime_cmp(&(pinfo
->abs_ts
), &m_first_frame_timestamp
) < 0)
454 nstime_copy(&(m_first_frame_timestamp
), &(pinfo
->abs_ts
));
459 nstime_copy(&(m_first_frame_timestamp
), &(pinfo
->abs_ts
));
460 m_first_frame_timestamp_valid
= true;
462 if (nstime_cmp(&(pinfo
->abs_ts
), &m_last_frame_timestamp
) > 0)
464 nstime_copy(&(m_last_frame_timestamp
), &(pinfo
->abs_ts
));
466 if (tap_info
->type
== LBTRM_PACKET_TYPE_DATA
)
468 LBMLBTRMSQNEntry
* sqn
= NULL
;
469 LBMLBTRMSQNMapIterator it
;
471 if (tap_info
->retransmission
)
474 m_rx_data_bytes
+= pinfo
->fd
->pkt_len
;
475 it
= m_rx_data_sqns
.find(tap_info
->sqn
);
476 if (m_rx_data_sqns
.end() == it
)
478 sqn
= new LBMLBTRMSQNEntry(tap_info
->sqn
);
479 m_rx_data_sqns
.insert(tap_info
->sqn
, sqn
);
489 m_data_bytes
+= pinfo
->fd
->pkt_len
;
490 it
= m_data_sqns
.find(tap_info
->sqn
);
491 if (m_data_sqns
.end() == it
)
493 sqn
= new LBMLBTRMSQNEntry(tap_info
->sqn
);
494 m_data_sqns
.insert(tap_info
->sqn
, sqn
);
501 sqn
->processFrame(pinfo
->num
);
503 else if (tap_info
->type
== LBTRM_PACKET_TYPE_NCF
)
506 LBMLBTRMNCFSQNMapIterator it
;
507 LBMLBTRMNCFSQNEntry
* sqn
= NULL
;
510 m_ncf_bytes
+= pinfo
->fd
->pkt_len
;
511 m_ncf_count
+= (uint64_t)tap_info
->num_sqns
;
512 for (idx
= 0; idx
< tap_info
->num_sqns
; idx
++)
514 it
= m_ncf_sqns
.find(tap_info
->sqns
[idx
]);
515 if (m_ncf_sqns
.end() == it
)
517 sqn
= new LBMLBTRMNCFSQNEntry(tap_info
->sqns
[idx
]);
518 m_ncf_sqns
.insert(tap_info
->sqns
[idx
], sqn
);
524 sqn
->processFrame(tap_info
->ncf_reason
, pinfo
->num
);
527 else if (tap_info
->type
== LBTRM_PACKET_TYPE_SM
)
529 LBMLBTRMSQNEntry
* sqn
= NULL
;
530 LBMLBTRMSQNMapIterator it
;
533 m_sm_bytes
+= pinfo
->fd
->pkt_len
;
534 it
= m_sm_sqns
.find(tap_info
->sqn
);
535 if (m_sm_sqns
.end() == it
)
537 sqn
= new LBMLBTRMSQNEntry(tap_info
->sqn
);
538 m_sm_sqns
.insert(tap_info
->sqn
, sqn
);
544 sqn
->processFrame(pinfo
->num
);
553 void LBMLBTRMSourceTransportEntry::fillItem(void)
557 nstime_delta(&delta
, &m_last_frame_timestamp
, &m_first_frame_timestamp
);
558 setText(Source_DataFrames_Column
, QStringLiteral("%1").arg(m_data_frames
));
559 setTextAlignment(Source_DataFrames_Column
, Qt::AlignRight
);
560 setText(Source_DataBytes_Column
, QStringLiteral("%1").arg(m_data_bytes
));
561 setTextAlignment(Source_DataBytes_Column
, Qt::AlignRight
);
562 setText(Source_DataFramesBytes_Column
, QStringLiteral("%1/%2").arg(m_data_frames
).arg(m_data_bytes
));
563 setTextAlignment(Source_DataFramesBytes_Column
, Qt::AlignHCenter
);
564 setText(Source_DataRate_Column
, format_rate(delta
, m_data_bytes
));
565 setTextAlignment(Source_DataRate_Column
, Qt::AlignRight
);
566 setText(Source_RXDataFrames_Column
, QStringLiteral("%1").arg(m_rx_data_frames
));
567 setTextAlignment(Source_RXDataFrames_Column
, Qt::AlignRight
);
568 setText(Source_RXDataBytes_Column
, QStringLiteral("%1").arg(m_rx_data_bytes
));
569 setTextAlignment(Source_RXDataBytes_Column
, Qt::AlignRight
);
570 setText(Source_RXDataFramesBytes_Column
, QStringLiteral("%1/%2").arg(m_rx_data_frames
).arg(m_rx_data_bytes
));
571 setTextAlignment(Source_RXDataFramesBytes_Column
, Qt::AlignHCenter
);
572 setText(Source_RXDataRate_Column
, format_rate(delta
, m_rx_data_bytes
));
573 setTextAlignment(Source_RXDataRate_Column
, Qt::AlignRight
);
574 setText(Source_NCFFrames_Column
, QStringLiteral("%1").arg(m_ncf_frames
));
575 setTextAlignment(Source_NCFFrames_Column
, Qt::AlignRight
);
576 setText(Source_NCFCount_Column
, QStringLiteral("%1").arg(m_ncf_count
));
577 setTextAlignment(Source_NCFCount_Column
, Qt::AlignRight
);
578 setText(Source_NCFBytes_Column
, QStringLiteral("%1").arg(m_ncf_bytes
));
579 setTextAlignment(Source_NCFBytes_Column
, Qt::AlignRight
);
580 setText(Source_NCFFramesBytes_Column
, QStringLiteral("%1/%2").arg(m_ncf_frames
).arg(m_ncf_bytes
));
581 setTextAlignment(Source_NCFFramesBytes_Column
, Qt::AlignHCenter
);
582 setText(Source_NCFCountBytes_Column
, QStringLiteral("%1/%2").arg(m_ncf_count
).arg(m_ncf_bytes
));
583 setTextAlignment(Source_NCFCountBytes_Column
, Qt::AlignHCenter
);
584 setText(Source_NCFFramesCount_Column
, QStringLiteral("%1/%2").arg(m_ncf_count
).arg(m_ncf_count
));
585 setTextAlignment(Source_NCFFramesCount_Column
, Qt::AlignHCenter
);
586 setText(Source_NCFFramesCountBytes_Column
, QStringLiteral("%1/%2/%3").arg(m_ncf_frames
).arg(m_ncf_count
).arg(m_ncf_bytes
));
587 setTextAlignment(Source_NCFFramesCountBytes_Column
, Qt::AlignHCenter
);
588 setText(Source_NCFRate_Column
, format_rate(delta
, m_ncf_bytes
));
589 setTextAlignment(Source_NCFRate_Column
, Qt::AlignRight
);
590 setText(Source_SMFrames_Column
, QStringLiteral("%1").arg(m_sm_frames
));
591 setTextAlignment(Source_SMFrames_Column
, Qt::AlignRight
);
592 setText(Source_SMBytes_Column
, QStringLiteral("%1").arg(m_sm_bytes
));
593 setTextAlignment(Source_SMBytes_Column
, Qt::AlignRight
);
594 setText(Source_SMFramesBytes_Column
, QStringLiteral("%1/%2").arg(m_sm_frames
).arg(m_sm_bytes
));
595 setTextAlignment(Source_SMFramesBytes_Column
, Qt::AlignHCenter
);
596 setText(Source_SMRate_Column
, format_rate(delta
, m_sm_bytes
));
597 setTextAlignment(Source_SMRate_Column
, Qt::AlignRight
);
600 typedef QMap
<QString
, LBMLBTRMSourceTransportEntry
*> LBMLBTRMSourceTransportMap
;
601 typedef QMap
<QString
, LBMLBTRMSourceTransportEntry
*>::iterator LBMLBTRMSourceTransportMapIterator
;
603 // A source (address) entry
604 class LBMLBTRMSourceEntry
: public QTreeWidgetItem
607 LBMLBTRMSourceEntry(const QString
& source_address
);
608 virtual ~LBMLBTRMSourceEntry(void);
609 void processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
);
615 uint64_t m_data_frames
;
616 uint64_t m_data_bytes
;
617 uint64_t m_rx_data_frames
;
618 uint64_t m_rx_data_bytes
;
619 uint64_t m_ncf_frames
;
620 uint64_t m_ncf_count
;
621 uint64_t m_ncf_bytes
;
622 uint64_t m_sm_frames
;
624 nstime_t m_first_frame_timestamp
;
625 bool m_first_frame_timestamp_valid
;
626 nstime_t m_last_frame_timestamp
;
627 LBMLBTRMSourceTransportMap m_transports
;
630 LBMLBTRMSourceEntry::LBMLBTRMSourceEntry(const QString
& source_address
) :
632 m_address(source_address
),
642 m_first_frame_timestamp_valid(false),
645 m_first_frame_timestamp
.secs
= 0;
646 m_first_frame_timestamp
.nsecs
= 0;
647 m_last_frame_timestamp
.secs
= 0;
648 m_last_frame_timestamp
.nsecs
= 0;
649 setText(Source_AddressTransport_Column
, m_address
);
652 LBMLBTRMSourceEntry::~LBMLBTRMSourceEntry(void)
654 for (LBMLBTRMSourceTransportMapIterator it
= m_transports
.begin(); it
!= m_transports
.end(); ++it
)
658 m_transports
.clear();
661 void LBMLBTRMSourceEntry::processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
)
663 LBMLBTRMSourceTransportEntry
* transport
= NULL
;
664 LBMLBTRMSourceTransportMapIterator it
;
666 if (m_first_frame_timestamp_valid
)
668 if (nstime_cmp(&(pinfo
->abs_ts
), &m_first_frame_timestamp
) < 0)
670 nstime_copy(&(m_first_frame_timestamp
), &(pinfo
->abs_ts
));
675 nstime_copy(&(m_first_frame_timestamp
), &(pinfo
->abs_ts
));
676 m_first_frame_timestamp_valid
= true;
678 if (nstime_cmp(&(pinfo
->abs_ts
), &m_last_frame_timestamp
) > 0)
680 nstime_copy(&(m_last_frame_timestamp
), &(pinfo
->abs_ts
));
682 if (tap_info
->type
== LBTRM_PACKET_TYPE_DATA
)
684 if (tap_info
->retransmission
)
687 m_rx_data_bytes
+= pinfo
->fd
->pkt_len
;
692 m_data_bytes
+= pinfo
->fd
->pkt_len
;
695 else if (tap_info
->type
== LBTRM_PACKET_TYPE_NCF
)
698 m_ncf_bytes
+= pinfo
->fd
->pkt_len
;
699 m_ncf_count
+= tap_info
->num_sqns
;
701 else if (tap_info
->type
== LBTRM_PACKET_TYPE_SM
)
704 m_sm_bytes
+= pinfo
->fd
->pkt_len
;
707 it
= m_transports
.find(tap_info
->transport
);
708 if (m_transports
.end() == it
)
710 transport
= new LBMLBTRMSourceTransportEntry(tap_info
->transport
);
711 m_transports
.insert(tap_info
->transport
, transport
);
713 sortChildren(Source_AddressTransport_Column
, Qt::AscendingOrder
);
717 transport
= it
.value();
720 transport
->processPacket(pinfo
, tap_info
);
723 void LBMLBTRMSourceEntry::fillItem(void)
727 nstime_delta(&delta
, &m_last_frame_timestamp
, &m_first_frame_timestamp
);
728 setText(Source_DataFrames_Column
, QStringLiteral("%1").arg(m_data_frames
));
729 setTextAlignment(Source_DataFrames_Column
, Qt::AlignRight
);
730 setText(Source_DataBytes_Column
, QStringLiteral("%1").arg(m_data_bytes
));
731 setTextAlignment(Source_DataBytes_Column
, Qt::AlignRight
);
732 setText(Source_DataFramesBytes_Column
, QStringLiteral("%1/%2").arg(m_data_frames
).arg(m_data_bytes
));
733 setTextAlignment(Source_DataFramesBytes_Column
, Qt::AlignHCenter
);
734 setText(Source_DataRate_Column
, format_rate(delta
, m_data_bytes
));
735 setTextAlignment(Source_DataRate_Column
, Qt::AlignRight
);
736 setText(Source_RXDataFrames_Column
, QStringLiteral("%1").arg(m_rx_data_frames
));
737 setTextAlignment(Source_RXDataFrames_Column
, Qt::AlignRight
);
738 setText(Source_RXDataBytes_Column
, QStringLiteral("%1").arg(m_rx_data_bytes
));
739 setTextAlignment(Source_RXDataBytes_Column
, Qt::AlignRight
);
740 setText(Source_RXDataFramesBytes_Column
, QStringLiteral("%1/%2").arg(m_rx_data_frames
).arg(m_rx_data_bytes
));
741 setTextAlignment(Source_RXDataFramesBytes_Column
, Qt::AlignHCenter
);
742 setText(Source_RXDataRate_Column
, format_rate(delta
, m_rx_data_bytes
));
743 setTextAlignment(Source_RXDataRate_Column
, Qt::AlignRight
);
744 setText(Source_NCFFrames_Column
, QStringLiteral("%1").arg(m_ncf_frames
));
745 setTextAlignment(Source_NCFFrames_Column
, Qt::AlignRight
);
746 setText(Source_NCFCount_Column
, QStringLiteral("%1").arg(m_ncf_count
));
747 setTextAlignment(Source_NCFCount_Column
, Qt::AlignRight
);
748 setText(Source_NCFBytes_Column
, QStringLiteral("%1").arg(m_ncf_bytes
));
749 setTextAlignment(Source_NCFBytes_Column
, Qt::AlignRight
);
750 setText(Source_NCFFramesBytes_Column
, QStringLiteral("%1/%2").arg(m_ncf_frames
).arg(m_ncf_bytes
));
751 setTextAlignment(Source_NCFFramesBytes_Column
, Qt::AlignHCenter
);
752 setText(Source_NCFCountBytes_Column
, QStringLiteral("%1/%2").arg(m_ncf_count
).arg(m_ncf_bytes
));
753 setTextAlignment(Source_NCFCountBytes_Column
, Qt::AlignHCenter
);
754 setText(Source_NCFFramesCount_Column
, QStringLiteral("%1/%2").arg(m_ncf_frames
).arg(m_ncf_count
));
755 setTextAlignment(Source_NCFFramesCount_Column
, Qt::AlignHCenter
);
756 setText(Source_NCFFramesCountBytes_Column
, QStringLiteral("%1/%2/%3").arg(m_ncf_frames
).arg(m_ncf_count
).arg(m_ncf_bytes
));
757 setTextAlignment(Source_NCFFramesCountBytes_Column
, Qt::AlignHCenter
);
758 setText(Source_NCFRate_Column
, format_rate(delta
, m_ncf_bytes
));
759 setTextAlignment(Source_NCFRate_Column
, Qt::AlignRight
);
760 setText(Source_SMFrames_Column
, QStringLiteral("%1").arg(m_sm_frames
));
761 setTextAlignment(Source_SMFrames_Column
, Qt::AlignRight
);
762 setText(Source_SMBytes_Column
, QStringLiteral("%1").arg(m_sm_bytes
));
763 setTextAlignment(Source_SMBytes_Column
, Qt::AlignRight
);
764 setText(Source_SMFramesBytes_Column
, QStringLiteral("%1/%2").arg(m_sm_frames
).arg(m_sm_bytes
));
765 setTextAlignment(Source_SMFramesBytes_Column
, Qt::AlignRight
);
766 setText(Source_SMRate_Column
, format_rate(delta
, m_sm_bytes
));
767 setTextAlignment(Source_SMRate_Column
, Qt::AlignRight
);
770 typedef QMap
<QString
, LBMLBTRMSourceEntry
*> LBMLBTRMSourceMap
;
771 typedef QMap
<QString
, LBMLBTRMSourceEntry
*>::iterator LBMLBTRMSourceMapIterator
;
773 // A receiver transport entry
774 class LBMLBTRMReceiverTransportEntry
: public QTreeWidgetItem
776 friend class LBMLBTRMTransportDialog
;
779 LBMLBTRMReceiverTransportEntry(const QString
& transport
);
780 virtual ~LBMLBTRMReceiverTransportEntry(void);
781 void processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
);
786 uint64_t m_nak_frames
;
787 uint64_t m_nak_count
;
788 uint64_t m_nak_bytes
;
789 nstime_t m_first_frame_timestamp
;
790 bool m_first_frame_timestamp_valid
;
791 nstime_t m_last_frame_timestamp
;
794 LBMLBTRMSQNMap m_nak_sqns
;
797 LBMLBTRMReceiverTransportEntry::LBMLBTRMReceiverTransportEntry(const QString
& transport
) :
799 m_transport(transport
),
803 m_first_frame_timestamp_valid(false),
806 m_first_frame_timestamp
.secs
= 0;
807 m_first_frame_timestamp
.nsecs
= 0;
808 m_last_frame_timestamp
.secs
= 0;
809 m_last_frame_timestamp
.nsecs
= 0;
810 setText(Receiver_AddressTransport_Column
, m_transport
);
813 LBMLBTRMReceiverTransportEntry::~LBMLBTRMReceiverTransportEntry(void)
815 for (LBMLBTRMSQNMapIterator it
= m_nak_sqns
.begin(); it
!= m_nak_sqns
.end(); ++it
)
822 void LBMLBTRMReceiverTransportEntry::processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
)
824 if (m_first_frame_timestamp_valid
)
826 if (nstime_cmp(&(pinfo
->abs_ts
), &m_first_frame_timestamp
) < 0)
828 nstime_copy(&(m_first_frame_timestamp
), &(pinfo
->abs_ts
));
833 nstime_copy(&(m_first_frame_timestamp
), &(pinfo
->abs_ts
));
834 m_first_frame_timestamp_valid
= true;
836 if (nstime_cmp(&(pinfo
->abs_ts
), &m_last_frame_timestamp
) > 0)
838 nstime_copy(&(m_last_frame_timestamp
), &(pinfo
->abs_ts
));
840 if (tap_info
->type
== LBTRM_PACKET_TYPE_NAK
)
843 LBMLBTRMSQNEntry
* sqn
= NULL
;
844 LBMLBTRMSQNMapIterator it
;
847 m_nak_bytes
+= pinfo
->fd
->pkt_len
;
848 m_nak_count
+= tap_info
->num_sqns
;
849 for (idx
= 0; idx
< tap_info
->num_sqns
; idx
++)
851 it
= m_nak_sqns
.find(tap_info
->sqns
[idx
]);
852 if (m_nak_sqns
.end() == it
)
854 sqn
= new LBMLBTRMSQNEntry(tap_info
->sqns
[idx
]);
855 m_nak_sqns
.insert(tap_info
->sqns
[idx
], sqn
);
861 sqn
->processFrame(pinfo
->num
);
871 void LBMLBTRMReceiverTransportEntry::fillItem(void)
875 nstime_delta(&delta
, &m_last_frame_timestamp
, &m_first_frame_timestamp
);
876 setText(Receiver_NAKFrames_Column
, QStringLiteral("%1").arg(m_nak_frames
));
877 setTextAlignment(Receiver_NAKFrames_Column
, Qt::AlignRight
);
878 setText(Receiver_NAKCount_Column
, QStringLiteral("%1").arg(m_nak_count
));
879 setTextAlignment(Receiver_NAKCount_Column
, Qt::AlignRight
);
880 setText(Receiver_NAKBytes_Column
, QStringLiteral("%1").arg(m_nak_bytes
));
881 setTextAlignment(Receiver_NAKBytes_Column
, Qt::AlignRight
);
882 setText(Receiver_NAKRate_Column
, format_rate(delta
, m_nak_bytes
));
883 setTextAlignment(Receiver_NAKRate_Column
, Qt::AlignRight
);
886 typedef QMap
<QString
, LBMLBTRMReceiverTransportEntry
*> LBMLBTRMReceiverTransportMap
;
887 typedef QMap
<QString
, LBMLBTRMReceiverTransportEntry
*>::iterator LBMLBTRMReceiverTransportMapIterator
;
889 // A receiver (address) entry
890 class LBMLBTRMReceiverEntry
: public QTreeWidgetItem
893 LBMLBTRMReceiverEntry(const QString
& receiver_address
);
894 virtual ~LBMLBTRMReceiverEntry(void);
895 void processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
);
898 LBMLBTRMReceiverEntry(void);
902 uint64_t m_nak_frames
;
903 uint64_t m_nak_count
;
904 uint64_t m_nak_bytes
;
905 nstime_t m_first_frame_timestamp
;
906 bool m_first_frame_timestamp_valid
;
907 nstime_t m_last_frame_timestamp
;
908 LBMLBTRMReceiverTransportMap m_transports
;
911 LBMLBTRMReceiverEntry::LBMLBTRMReceiverEntry(const QString
& receiver_address
) :
913 m_address(receiver_address
),
917 m_first_frame_timestamp_valid(false),
920 m_first_frame_timestamp
.secs
= 0;
921 m_first_frame_timestamp
.nsecs
= 0;
922 m_last_frame_timestamp
.secs
= 0;
923 m_last_frame_timestamp
.nsecs
= 0;
924 setText(Receiver_AddressTransport_Column
, m_address
);
927 LBMLBTRMReceiverEntry::~LBMLBTRMReceiverEntry(void)
929 for (LBMLBTRMReceiverTransportMapIterator it
= m_transports
.begin(); it
!= m_transports
.end(); ++it
)
933 m_transports
.clear();
936 void LBMLBTRMReceiverEntry::processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
)
938 LBMLBTRMReceiverTransportEntry
* transport
= NULL
;
939 LBMLBTRMReceiverTransportMapIterator it
;
941 if (m_first_frame_timestamp_valid
)
943 if (nstime_cmp(&(pinfo
->abs_ts
), &m_first_frame_timestamp
) < 0)
945 nstime_copy(&(m_first_frame_timestamp
), &(pinfo
->abs_ts
));
950 nstime_copy(&(m_first_frame_timestamp
), &(pinfo
->abs_ts
));
951 m_first_frame_timestamp_valid
= true;
953 if (nstime_cmp(&(pinfo
->abs_ts
), &m_last_frame_timestamp
) > 0)
955 nstime_copy(&(m_last_frame_timestamp
), &(pinfo
->abs_ts
));
957 if (tap_info
->type
== LBTRM_PACKET_TYPE_NAK
)
960 m_nak_bytes
+= pinfo
->fd
->pkt_len
;
961 m_nak_count
+= tap_info
->num_sqns
;
964 it
= m_transports
.find(tap_info
->transport
);
965 if (m_transports
.end() == it
)
967 transport
= new LBMLBTRMReceiverTransportEntry(tap_info
->transport
);
968 m_transports
.insert(tap_info
->transport
, transport
);
970 sortChildren(Receiver_AddressTransport_Column
, Qt::AscendingOrder
);
974 transport
= it
.value();
977 transport
->processPacket(pinfo
, tap_info
);
980 void LBMLBTRMReceiverEntry::fillItem(void)
984 nstime_delta(&delta
, &m_last_frame_timestamp
, &m_first_frame_timestamp
);
985 setText(Receiver_NAKFrames_Column
, QStringLiteral("%1").arg(m_nak_frames
));
986 setTextAlignment(Receiver_NAKFrames_Column
, Qt::AlignRight
);
987 setText(Receiver_NAKCount_Column
, QStringLiteral("%1").arg(m_nak_count
));
988 setTextAlignment(Receiver_NAKCount_Column
, Qt::AlignRight
);
989 setText(Receiver_NAKBytes_Column
, QStringLiteral("%1").arg(m_nak_bytes
));
990 setTextAlignment(Receiver_NAKBytes_Column
, Qt::AlignRight
);
991 setText(Receiver_NAKRate_Column
, format_rate(delta
, m_nak_bytes
));
992 setTextAlignment(Receiver_NAKRate_Column
, Qt::AlignRight
);
995 typedef QMap
<QString
, LBMLBTRMReceiverEntry
*> LBMLBTRMReceiverMap
;
996 typedef QMap
<QString
, LBMLBTRMReceiverEntry
*>::iterator LBMLBTRMReceiverMapIterator
;
998 class LBMLBTRMTransportDialogInfo
1001 LBMLBTRMTransportDialogInfo(void);
1002 ~LBMLBTRMTransportDialogInfo(void);
1003 void setDialog(LBMLBTRMTransportDialog
* dialog
);
1004 LBMLBTRMTransportDialog
* getDialog(void);
1005 void processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
);
1006 void clearMaps(void);
1009 LBMLBTRMTransportDialog
* m_dialog
;
1010 LBMLBTRMSourceMap m_sources
;
1011 LBMLBTRMReceiverMap m_receivers
;
1014 LBMLBTRMTransportDialogInfo::LBMLBTRMTransportDialogInfo(void) :
1021 LBMLBTRMTransportDialogInfo::~LBMLBTRMTransportDialogInfo(void)
1026 void LBMLBTRMTransportDialogInfo::setDialog(LBMLBTRMTransportDialog
* dialog
)
1031 LBMLBTRMTransportDialog
* LBMLBTRMTransportDialogInfo::getDialog(void)
1036 void LBMLBTRMTransportDialogInfo::processPacket(const packet_info
* pinfo
, const lbm_lbtrm_tap_info_t
* tap_info
)
1038 switch (tap_info
->type
)
1040 case LBTRM_PACKET_TYPE_DATA
:
1041 case LBTRM_PACKET_TYPE_SM
:
1042 case LBTRM_PACKET_TYPE_NCF
:
1044 LBMLBTRMSourceEntry
* source
= NULL
;
1045 LBMLBTRMSourceMapIterator it
;
1046 QString src_address
= address_to_qstring(&(pinfo
->src
));
1048 it
= m_sources
.find(src_address
);
1049 if (m_sources
.end() == it
)
1051 QTreeWidgetItem
* parent
= NULL
;
1052 Ui::LBMLBTRMTransportDialog
* ui
= NULL
;
1054 source
= new LBMLBTRMSourceEntry(src_address
);
1055 it
= m_sources
.insert(src_address
, source
);
1056 ui
= m_dialog
->getUI();
1057 ui
->sources_TreeWidget
->addTopLevelItem(source
);
1058 parent
= ui
->sources_TreeWidget
->invisibleRootItem();
1059 parent
->sortChildren(Source_AddressTransport_Column
, Qt::AscendingOrder
);
1060 ui
->sources_TreeWidget
->resizeColumnToContents(Source_AddressTransport_Column
);
1064 source
= it
.value();
1066 source
->processPacket(pinfo
, tap_info
);
1069 case LBTRM_PACKET_TYPE_NAK
:
1071 LBMLBTRMReceiverEntry
* receiver
= NULL
;
1072 LBMLBTRMReceiverMapIterator it
;
1073 QString src_address
= address_to_qstring(&(pinfo
->src
));
1075 it
= m_receivers
.find(src_address
);
1076 if (m_receivers
.end() == it
)
1078 QTreeWidgetItem
* parent
= NULL
;
1079 Ui::LBMLBTRMTransportDialog
* ui
= NULL
;
1081 receiver
= new LBMLBTRMReceiverEntry(src_address
);
1082 it
= m_receivers
.insert(src_address
, receiver
);
1083 ui
= m_dialog
->getUI();
1084 ui
->receivers_TreeWidget
->addTopLevelItem(receiver
);
1085 parent
= ui
->receivers_TreeWidget
->invisibleRootItem();
1086 parent
->sortChildren(Receiver_AddressTransport_Column
, Qt::AscendingOrder
);
1087 ui
->receivers_TreeWidget
->resizeColumnToContents(Receiver_AddressTransport_Column
);
1091 receiver
= it
.value();
1093 receiver
->processPacket(pinfo
, tap_info
);
1101 void LBMLBTRMTransportDialogInfo::clearMaps(void)
1103 for (LBMLBTRMSourceMapIterator it
= m_sources
.begin(); it
!= m_sources
.end(); ++it
)
1109 for (LBMLBTRMReceiverMapIterator it
= m_receivers
.begin(); it
!= m_receivers
.end(); ++it
)
1113 m_receivers
.clear();
1116 LBMLBTRMTransportDialog::LBMLBTRMTransportDialog(QWidget
* parent
, capture_file
* cfile
) :
1118 m_ui(new Ui::LBMLBTRMTransportDialog
),
1119 m_dialog_info(NULL
),
1120 m_capture_file(cfile
),
1121 m_current_source_transport(NULL
),
1122 m_current_receiver_transport(NULL
),
1123 m_source_context_menu(NULL
),
1124 m_source_header(NULL
)
1126 m_ui
->setupUi(this);
1127 m_dialog_info
= new LBMLBTRMTransportDialogInfo();
1129 m_ui
->tabWidget
->setCurrentIndex(0);
1130 m_ui
->sources_detail_ComboBox
->setCurrentIndex(0);
1131 m_ui
->sources_detail_transport_Label
->setText(QStringLiteral(" "));
1132 m_ui
->receivers_detail_transport_Label
->setText(QStringLiteral(" "));
1133 m_ui
->stackedWidget
->setCurrentIndex(0);
1135 m_source_header
= m_ui
->sources_TreeWidget
->header();
1136 m_source_context_menu
= new QMenu(m_source_header
);
1138 m_source_context_menu
->addAction(m_ui
->action_SourceAutoResizeColumns
);
1139 connect(m_ui
->action_SourceAutoResizeColumns
, SIGNAL(triggered()), this, SLOT(actionSourceAutoResizeColumns_triggered()));
1140 m_source_context_menu
->addSeparator();
1142 m_ui
->action_SourceDataFrames
->setChecked(true);
1143 m_source_context_menu
->addAction(m_ui
->action_SourceDataFrames
);
1144 connect(m_ui
->action_SourceDataFrames
, SIGNAL(triggered(bool)), this, SLOT(actionSourceDataFrames_triggered(bool)));
1145 m_ui
->action_SourceDataBytes
->setChecked(true);
1146 m_source_context_menu
->addAction(m_ui
->action_SourceDataBytes
);
1147 connect(m_ui
->action_SourceDataBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceDataBytes_triggered(bool)));
1148 m_ui
->action_SourceDataFramesBytes
->setChecked(false);
1149 m_source_context_menu
->addAction(m_ui
->action_SourceDataFramesBytes
);
1150 connect(m_ui
->action_SourceDataFramesBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceDataFramesBytes_triggered(bool)));
1151 m_ui
->action_SourceDataRate
->setChecked(true);
1152 m_source_context_menu
->addAction(m_ui
->action_SourceDataRate
);
1153 connect(m_ui
->action_SourceDataRate
, SIGNAL(triggered(bool)), this, SLOT(actionSourceDataRate_triggered(bool)));
1155 m_ui
->action_SourceRXDataFrames
->setChecked(true);
1156 m_source_context_menu
->addAction(m_ui
->action_SourceRXDataFrames
);
1157 connect(m_ui
->action_SourceRXDataFrames
, SIGNAL(triggered(bool)), this, SLOT(actionSourceRXDataFrames_triggered(bool)));
1158 m_ui
->action_SourceRXDataBytes
->setChecked(true);
1159 m_source_context_menu
->addAction(m_ui
->action_SourceRXDataBytes
);
1160 connect(m_ui
->action_SourceRXDataBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceRXDataBytes_triggered(bool)));
1161 m_ui
->action_SourceRXDataFramesBytes
->setChecked(false);
1162 m_source_context_menu
->addAction(m_ui
->action_SourceRXDataFramesBytes
);
1163 connect(m_ui
->action_SourceRXDataFramesBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceRXDataFramesBytes_triggered(bool)));
1164 m_ui
->action_SourceRXDataRate
->setChecked(true);
1165 m_source_context_menu
->addAction(m_ui
->action_SourceRXDataRate
);
1166 connect(m_ui
->action_SourceRXDataRate
, SIGNAL(triggered(bool)), this, SLOT(actionSourceRXDataRate_triggered(bool)));
1168 m_ui
->action_SourceNCFFrames
->setChecked(true);
1169 m_source_context_menu
->addAction(m_ui
->action_SourceNCFFrames
);
1170 connect(m_ui
->action_SourceNCFFrames
, SIGNAL(triggered(bool)), this, SLOT(actionSourceNCFFrames_triggered(bool)));
1171 m_ui
->action_SourceNCFCount
->setChecked(true);
1172 m_source_context_menu
->addAction(m_ui
->action_SourceNCFCount
);
1173 connect(m_ui
->action_SourceNCFCount
, SIGNAL(triggered(bool)), this, SLOT(actionSourceNCFCount_triggered(bool)));
1174 m_ui
->action_SourceNCFBytes
->setChecked(true);
1175 m_source_context_menu
->addAction(m_ui
->action_SourceNCFBytes
);
1176 connect(m_ui
->action_SourceNCFBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceNCFBytes_triggered(bool)));
1177 m_ui
->action_SourceNCFFramesBytes
->setChecked(false);
1178 m_source_context_menu
->addAction(m_ui
->action_SourceNCFFramesBytes
);
1179 connect(m_ui
->action_SourceNCFFramesBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceNCFFramesBytes_triggered(bool)));
1180 m_ui
->action_SourceNCFCountBytes
->setChecked(false);
1181 m_source_context_menu
->addAction(m_ui
->action_SourceNCFCountBytes
);
1182 connect(m_ui
->action_SourceNCFCountBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceNCFCountBytes_triggered(bool)));
1183 m_ui
->action_SourceNCFFramesCount
->setChecked(false);
1184 m_source_context_menu
->addAction(m_ui
->action_SourceNCFFramesCount
);
1185 connect(m_ui
->action_SourceNCFFramesCount
, SIGNAL(triggered(bool)), this, SLOT(actionSourceNCFFramesCount_triggered(bool)));
1186 m_ui
->action_SourceNCFFramesCountBytes
->setChecked(false);
1187 m_source_context_menu
->addAction(m_ui
->action_SourceNCFFramesCountBytes
);
1188 connect(m_ui
->action_SourceNCFFramesCountBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceNCFFramesCountBytes_triggered(bool)));
1189 m_ui
->action_SourceNCFRate
->setChecked(true);
1190 m_source_context_menu
->addAction(m_ui
->action_SourceNCFRate
);
1191 connect(m_ui
->action_SourceNCFRate
, SIGNAL(triggered(bool)), this, SLOT(actionSourceNCFRate_triggered(bool)));
1193 m_ui
->action_SourceSMFrames
->setChecked(true);
1194 m_source_context_menu
->addAction(m_ui
->action_SourceSMFrames
);
1195 connect(m_ui
->action_SourceSMFrames
, SIGNAL(triggered(bool)), this, SLOT(actionSourceSMFrames_triggered(bool)));
1196 m_ui
->action_SourceSMBytes
->setChecked(true);
1197 m_source_context_menu
->addAction(m_ui
->action_SourceSMBytes
);
1198 connect(m_ui
->action_SourceSMBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceSMBytes_triggered(bool)));
1199 m_ui
->action_SourceSMFramesBytes
->setChecked(false);
1200 m_source_context_menu
->addAction(m_ui
->action_SourceSMFramesBytes
);
1201 connect(m_ui
->action_SourceSMFramesBytes
, SIGNAL(triggered(bool)), this, SLOT(actionSourceSMFramesBytes_triggered(bool)));
1202 m_ui
->action_SourceSMRate
->setChecked(true);
1203 m_source_context_menu
->addAction(m_ui
->action_SourceSMRate
);
1204 connect(m_ui
->action_SourceSMRate
, SIGNAL(triggered(bool)), this, SLOT(actionSourceSMRate_triggered(bool)));
1206 m_source_header
->setContextMenuPolicy(Qt::CustomContextMenu
);
1207 connect(m_source_header
, SIGNAL(customContextMenuRequested(const QPoint
&)), this, SLOT(custom_source_context_menuRequested(const QPoint
&)));
1209 m_ui
->sources_TreeWidget
->setColumnHidden(Source_DataFramesBytes_Column
, true);
1210 m_ui
->sources_TreeWidget
->setColumnHidden(Source_RXDataFramesBytes_Column
, true);
1211 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFFramesBytes_Column
, true);
1212 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFCountBytes_Column
, true);
1213 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFFramesCount_Column
, true);
1214 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFFramesCountBytes_Column
, true);
1215 m_ui
->sources_TreeWidget
->setColumnHidden(Source_SMFramesBytes_Column
, true);
1217 setAttribute(Qt::WA_DeleteOnClose
, true);
1221 LBMLBTRMTransportDialog::~LBMLBTRMTransportDialog(void)
1223 resetSourcesDetail();
1225 resetReceiversDetail();
1227 if (m_dialog_info
!= NULL
)
1229 delete m_dialog_info
;
1230 m_dialog_info
= NULL
;
1232 delete m_source_context_menu
;
1233 m_source_context_menu
= NULL
;
1236 m_capture_file
= NULL
;
1239 void LBMLBTRMTransportDialog::setCaptureFile(capture_file
* cfile
)
1241 if (cfile
== NULL
) // We only want to know when the file closes.
1243 m_capture_file
= NULL
;
1244 m_ui
->displayFilterLineEdit
->setEnabled(false);
1245 m_ui
->applyFilterButton
->setEnabled(false);
1249 void LBMLBTRMTransportDialog::resetSources(void)
1251 while (m_ui
->sources_TreeWidget
->takeTopLevelItem(0) != NULL
)
1255 void LBMLBTRMTransportDialog::resetReceivers(void)
1257 while (m_ui
->receivers_TreeWidget
->takeTopLevelItem(0) != NULL
)
1261 void LBMLBTRMTransportDialog::resetSourcesDetail(void)
1263 while (m_ui
->sources_detail_sqn_TreeWidget
->takeTopLevelItem(0) != NULL
)
1265 while (m_ui
->sources_detail_ncf_sqn_TreeWidget
->takeTopLevelItem(0) != NULL
)
1267 m_ui
->sources_detail_transport_Label
->setText(QStringLiteral(" "));
1268 m_current_source_transport
= NULL
;
1271 void LBMLBTRMTransportDialog::resetReceiversDetail(void)
1273 while (m_ui
->receivers_detail_TreeWidget
->takeTopLevelItem(0) != NULL
)
1275 m_ui
->receivers_detail_transport_Label
->setText(QStringLiteral(" "));
1276 m_current_receiver_transport
= NULL
;
1279 void LBMLBTRMTransportDialog::fillTree(void)
1281 GString
* error_string
;
1283 if (m_capture_file
== NULL
)
1287 m_dialog_info
->setDialog(this);
1289 error_string
= register_tap_listener("lbm_lbtrm",
1290 (void *)m_dialog_info
,
1291 m_ui
->displayFilterLineEdit
->text().toUtf8().constData(),
1292 TL_REQUIRES_COLUMNS
,
1299 QMessageBox::critical(this, tr("LBT-RM Statistics failed to attach to tap"),
1301 g_string_free(error_string
, TRUE
);
1305 cf_retap_packets(m_capture_file
);
1306 drawTreeItems(&m_dialog_info
);
1307 remove_tap_listener((void *)m_dialog_info
);
1310 void LBMLBTRMTransportDialog::resetTap(void * tap_data
)
1312 LBMLBTRMTransportDialogInfo
* info
= (LBMLBTRMTransportDialogInfo
*) tap_data
;
1313 LBMLBTRMTransportDialog
* dialog
= info
->getDialog();
1318 dialog
->resetSourcesDetail();
1319 dialog
->resetSources();
1320 dialog
->resetReceiversDetail();
1321 dialog
->resetReceivers();
1325 tap_packet_status
LBMLBTRMTransportDialog::tapPacket(void * tap_data
, packet_info
* pinfo
, epan_dissect_t
*, const void * tap_info
, tap_flags_t
)
1327 if (pinfo
->fd
->passed_dfilter
== 1)
1329 const lbm_lbtrm_tap_info_t
* tapinfo
= (const lbm_lbtrm_tap_info_t
*)tap_info
;
1330 LBMLBTRMTransportDialogInfo
* info
= (LBMLBTRMTransportDialogInfo
*)tap_data
;
1332 info
->processPacket(pinfo
, tapinfo
);
1334 return (TAP_PACKET_REDRAW
);
1337 void LBMLBTRMTransportDialog::drawTreeItems(void *)
1341 void LBMLBTRMTransportDialog::on_applyFilterButton_clicked(void)
1346 void LBMLBTRMTransportDialog::sourcesDetailCurrentChanged(int index
)
1357 m_ui
->stackedWidget
->setCurrentIndex(0);
1360 m_ui
->stackedWidget
->setCurrentIndex(1);
1365 sourcesItemClicked(m_current_source_transport
, 0);
1368 void LBMLBTRMTransportDialog::sourcesItemClicked(QTreeWidgetItem
* item
, int)
1370 LBMLBTRMSourceTransportEntry
* transport
= dynamic_cast<LBMLBTRMSourceTransportEntry
*>(item
);
1372 resetSourcesDetail();
1373 if (transport
== NULL
)
1375 // Must be a source item, ignore it?
1378 m_current_source_transport
= transport
;
1379 m_ui
->sources_detail_transport_Label
->setText(transport
->m_transport
);
1380 int cur_idx
= m_ui
->sources_detail_ComboBox
->currentIndex();
1384 loadSourceDataDetails(transport
);
1387 loadSourceRXDataDetails(transport
);
1390 loadSourceNCFDetails(transport
);
1393 loadSourceSMDetails(transport
);
1400 void LBMLBTRMTransportDialog::loadSourceDataDetails(LBMLBTRMSourceTransportEntry
* transport
)
1402 for (LBMLBTRMSQNMapIterator it
= transport
->m_data_sqns
.begin(); it
!= transport
->m_data_sqns
.end(); ++it
)
1404 LBMLBTRMSQNEntry
* sqn
= it
.value();
1405 m_ui
->sources_detail_sqn_TreeWidget
->addTopLevelItem(sqn
);
1409 void LBMLBTRMTransportDialog::loadSourceRXDataDetails(LBMLBTRMSourceTransportEntry
* transport
)
1411 for (LBMLBTRMSQNMapIterator it
= transport
->m_rx_data_sqns
.begin(); it
!= transport
->m_rx_data_sqns
.end(); ++it
)
1413 LBMLBTRMSQNEntry
* sqn
= it
.value();
1414 m_ui
->sources_detail_sqn_TreeWidget
->addTopLevelItem(sqn
);
1418 void LBMLBTRMTransportDialog::loadSourceNCFDetails(LBMLBTRMSourceTransportEntry
* transport
)
1420 for (LBMLBTRMNCFSQNMapIterator it
= transport
->m_ncf_sqns
.begin(); it
!= transport
->m_ncf_sqns
.end(); ++it
)
1422 LBMLBTRMNCFSQNEntry
* sqn
= it
.value();
1423 m_ui
->sources_detail_ncf_sqn_TreeWidget
->addTopLevelItem(sqn
);
1427 void LBMLBTRMTransportDialog::loadSourceSMDetails(LBMLBTRMSourceTransportEntry
* transport
)
1429 for (LBMLBTRMSQNMapIterator it
= transport
->m_sm_sqns
.begin(); it
!= transport
->m_sm_sqns
.end(); ++it
)
1431 LBMLBTRMSQNEntry
* sqn
= it
.value();
1432 m_ui
->sources_detail_sqn_TreeWidget
->addTopLevelItem(sqn
);
1436 void LBMLBTRMTransportDialog::receiversItemClicked(QTreeWidgetItem
* item
, int)
1438 LBMLBTRMReceiverTransportEntry
* transport
= dynamic_cast<LBMLBTRMReceiverTransportEntry
*>(item
);
1440 resetReceiversDetail();
1441 if (transport
== NULL
)
1443 // Must be a receiver item, ignore it?
1446 m_current_receiver_transport
= transport
;
1447 m_ui
->receivers_detail_transport_Label
->setText(transport
->m_transport
);
1448 loadReceiverNAKDetails(transport
);
1451 void LBMLBTRMTransportDialog::loadReceiverNAKDetails(LBMLBTRMReceiverTransportEntry
* transport
)
1453 for (LBMLBTRMSQNMapIterator it
= transport
->m_nak_sqns
.begin(); it
!= transport
->m_nak_sqns
.end(); ++it
)
1455 LBMLBTRMSQNEntry
* sqn
= it
.value();
1456 m_ui
->receivers_detail_TreeWidget
->addTopLevelItem(sqn
);
1460 void LBMLBTRMTransportDialog::sourcesDetailItemDoubleClicked(QTreeWidgetItem
* item
, int)
1462 LBMLBTRMFrameEntry
* frame
= dynamic_cast<LBMLBTRMFrameEntry
*>(item
);
1465 // Must have double-clicked on something other than an expanded frame entry
1468 emit
goToPacket((int)frame
->getFrame());
1471 void LBMLBTRMTransportDialog::receiversDetailItemDoubleClicked(QTreeWidgetItem
* item
, int)
1473 LBMLBTRMFrameEntry
* frame
= dynamic_cast<LBMLBTRMFrameEntry
*>(item
);
1476 // Must have double-clicked on something other than an expanded frame entry
1479 emit
goToPacket((int)frame
->getFrame());
1482 void LBMLBTRMTransportDialog::custom_source_context_menuRequested(const QPoint
& pos
)
1484 m_source_context_menu
->popup(m_source_header
->mapToGlobal(pos
));
1487 void LBMLBTRMTransportDialog::actionSourceDataFrames_triggered(bool checked
)
1489 m_ui
->sources_TreeWidget
->setColumnHidden(Source_DataFrames_Column
, !checked
);
1492 void LBMLBTRMTransportDialog::actionSourceDataBytes_triggered(bool checked
)
1494 m_ui
->sources_TreeWidget
->setColumnHidden(Source_DataBytes_Column
, !checked
);
1497 void LBMLBTRMTransportDialog::actionSourceDataFramesBytes_triggered(bool checked
)
1499 m_ui
->sources_TreeWidget
->setColumnHidden(Source_DataFramesBytes_Column
, !checked
);
1502 void LBMLBTRMTransportDialog::actionSourceDataRate_triggered(bool checked
)
1504 m_ui
->sources_TreeWidget
->setColumnHidden(Source_DataRate_Column
, !checked
);
1507 void LBMLBTRMTransportDialog::actionSourceRXDataFrames_triggered(bool checked
)
1509 m_ui
->sources_TreeWidget
->setColumnHidden(Source_RXDataFrames_Column
, !checked
);
1512 void LBMLBTRMTransportDialog::actionSourceRXDataBytes_triggered(bool checked
)
1514 m_ui
->sources_TreeWidget
->setColumnHidden(Source_RXDataBytes_Column
, !checked
);
1517 void LBMLBTRMTransportDialog::actionSourceRXDataFramesBytes_triggered(bool checked
)
1519 m_ui
->sources_TreeWidget
->setColumnHidden(Source_RXDataFramesBytes_Column
, !checked
);
1522 void LBMLBTRMTransportDialog::actionSourceRXDataRate_triggered(bool checked
)
1524 m_ui
->sources_TreeWidget
->setColumnHidden(Source_RXDataRate_Column
, !checked
);
1527 void LBMLBTRMTransportDialog::actionSourceNCFFrames_triggered(bool checked
)
1529 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFFrames_Column
, !checked
);
1532 void LBMLBTRMTransportDialog::actionSourceNCFCount_triggered(bool checked
)
1534 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFCount_Column
, !checked
);
1537 void LBMLBTRMTransportDialog::actionSourceNCFBytes_triggered(bool checked
)
1539 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFFrames_Column
, !checked
);
1542 void LBMLBTRMTransportDialog::actionSourceNCFFramesBytes_triggered(bool checked
)
1544 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFFramesBytes_Column
, !checked
);
1547 void LBMLBTRMTransportDialog::actionSourceNCFCountBytes_triggered(bool checked
)
1549 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFCountBytes_Column
, !checked
);
1552 void LBMLBTRMTransportDialog::actionSourceNCFFramesCount_triggered(bool checked
)
1554 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFFramesCount_Column
, !checked
);
1557 void LBMLBTRMTransportDialog::actionSourceNCFFramesCountBytes_triggered(bool checked
)
1559 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFFramesCountBytes_Column
, !checked
);
1562 void LBMLBTRMTransportDialog::actionSourceNCFRate_triggered(bool checked
)
1564 m_ui
->sources_TreeWidget
->setColumnHidden(Source_NCFRate_Column
, !checked
);
1567 void LBMLBTRMTransportDialog::actionSourceSMFrames_triggered(bool checked
)
1569 m_ui
->sources_TreeWidget
->setColumnHidden(Source_SMFrames_Column
, !checked
);
1572 void LBMLBTRMTransportDialog::actionSourceSMBytes_triggered(bool checked
)
1574 m_ui
->sources_TreeWidget
->setColumnHidden(Source_SMBytes_Column
, !checked
);
1577 void LBMLBTRMTransportDialog::actionSourceSMFramesBytes_triggered(bool checked
)
1579 m_ui
->sources_TreeWidget
->setColumnHidden(Source_SMFramesBytes_Column
, !checked
);
1582 void LBMLBTRMTransportDialog::actionSourceSMRate_triggered(bool checked
)
1584 m_ui
->sources_TreeWidget
->setColumnHidden(Source_SMRate_Column
, !checked
);
1587 void LBMLBTRMTransportDialog::actionSourceAutoResizeColumns_triggered(void)
1589 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_AddressTransport_Column
);
1590 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_DataFrames_Column
);
1591 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_DataBytes_Column
);
1592 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_DataFramesBytes_Column
);
1593 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_DataRate_Column
);
1594 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_RXDataFrames_Column
);
1595 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_RXDataBytes_Column
);
1596 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_RXDataFramesBytes_Column
);
1597 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_RXDataRate_Column
);
1598 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_NCFFrames_Column
);
1599 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_NCFCount_Column
);
1600 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_NCFBytes_Column
);
1601 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_NCFFramesBytes_Column
);
1602 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_NCFCountBytes_Column
);
1603 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_NCFFramesCount_Column
);
1604 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_NCFFramesCountBytes_Column
);
1605 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_NCFRate_Column
);
1606 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_SMFrames_Column
);
1607 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_SMBytes_Column
);
1608 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_SMFramesBytes_Column
);
1609 m_ui
->sources_TreeWidget
->resizeColumnToContents(Source_SMRate_Column
);