summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPeter Wu <peter@lekensteyn.nl>2015-11-17 18:54:41 +0100
committerGerald Combs <gerald@wireshark.org>2015-11-17 22:49:47 +0000
commitd92a5fa7b3404723cc23b9a83988c5e5bdd5456b (patch)
treeb5831f7a6756a1ca93a05eeabff8f68ae63dd7f6
parent804ee98b32bfd3fe39e67210da5569da8336ecda (diff)
downloadwireshark-d92a5fa7b3404723cc23b9a83988c5e5bdd5456b.tar.gz
Fix crash in RTP Player on stop and close
When dragging the UI, this somehow causes a great lag. Then by spam-clicking on the Stop button, a double free seems to occur. Fix this by moving the audio cleanup to the outputStateChanged callback as documented at https://doc.qt.io/qt-5/qaudiooutput.html. Note that calling stop() in the IdleState also triggers a change event, resulting in the desired cleanup. Stop streams before the dialog is closed (via accept/reject). This *cannot* be done in the destrutor of RtpPlayerDialog because destructing QAudioOutput processes events from the event queue, resulting in preature destruction of other objects... crash. Change-Id: I6bfb33c9396e9bc1ffd346519d22390a97b6bdaf Reviewed-on: https://code.wireshark.org/review/11894 Petri-Dish: Peter Wu <peter@lekensteyn.nl> Tested-by: Petri Dish Buildbot <buildbot-no-reply@wireshark.org> Reviewed-by: Gerald Combs <gerald@wireshark.org> (cherry picked from commit 0fef9d752f801986a81b7c294143eae21cd0de97) Reviewed-on: https://code.wireshark.org/review/11930
-rw-r--r--ui/qt/rtp_audio_stream.cpp16
-rw-r--r--ui/qt/rtp_player_dialog.cpp17
-rw-r--r--ui/qt/rtp_player_dialog.h3
3 files changed, 28 insertions, 8 deletions
diff --git a/ui/qt/rtp_audio_stream.cpp b/ui/qt/rtp_audio_stream.cpp
index 94149fe3ca..c16eca903c 100644
--- a/ui/qt/rtp_audio_stream.cpp
+++ b/ui/qt/rtp_audio_stream.cpp
@@ -539,10 +539,7 @@ void RtpAudioStream::stopPlaying()
{
if (audio_output_) {
audio_output_->stop();
- delete audio_output_;
- audio_output_ = NULL;
}
- emit finishedPlaying();
}
void RtpAudioStream::writeSilence(int samples)
@@ -564,20 +561,23 @@ void RtpAudioStream::writeSilence(int samples)
void RtpAudioStream::outputStateChanged()
{
- if (!audio_output_) return;
-
- if (audio_output_->state() == QAudio::IdleState) {
+ switch (audio_output_->state()) {
+ case QAudio::StoppedState:
// RTP_STREAM_DEBUG("stopped %f", audio_output_->processedUSecs() / 100000.0);
delete audio_output_;
audio_output_ = NULL;
-
emit finishedPlaying();
+ break;
+ case QAudio::IdleState:
+ audio_output_->stop();
+ break;
+ default:
+ break;
}
}
void RtpAudioStream::outputNotify()
{
- if (!audio_output_) return;
emit processedSecs(audio_output_->processedUSecs() / 1000000.0);
}
diff --git a/ui/qt/rtp_player_dialog.cpp b/ui/qt/rtp_player_dialog.cpp
index e5545c99d9..9b26c1fb5a 100644
--- a/ui/qt/rtp_player_dialog.cpp
+++ b/ui/qt/rtp_player_dialog.cpp
@@ -177,6 +177,23 @@ RtpPlayerDialog::~RtpPlayerDialog()
delete ui;
}
+void RtpPlayerDialog::accept()
+{
+ int row_count = ui->streamTreeWidget->topLevelItemCount();
+ // Stop all streams before the dialogs are closed.
+ for (int row = 0; row < row_count; row++) {
+ QTreeWidgetItem *ti = ui->streamTreeWidget->topLevelItem(row);
+ RtpAudioStream *audio_stream = ti->data(stream_data_col_, Qt::UserRole).value<RtpAudioStream*>();
+ audio_stream->stopPlaying();
+ }
+ WiresharkDialog::accept();
+}
+
+void RtpPlayerDialog::reject()
+{
+ RtpPlayerDialog::accept();
+}
+
void RtpPlayerDialog::retapPackets()
{
register_tap_listener("rtp", this, NULL, 0, NULL, tapPacket, NULL);
diff --git a/ui/qt/rtp_player_dialog.h b/ui/qt/rtp_player_dialog.h
index be3f2c57c1..5f214682da 100644
--- a/ui/qt/rtp_player_dialog.h
+++ b/ui/qt/rtp_player_dialog.h
@@ -61,6 +61,9 @@ public:
#ifdef QT_MULTIMEDIA_LIB
~RtpPlayerDialog();
+ void accept();
+ void reject();
+
/** Add an RTP stream to play.
* MUST be called before exec().
* Requires src_addr, src_port, dest_addr, dest_port, ssrc, packet_count,