summaryrefslogtreecommitdiffstats
path: root/content/browser/media
diff options
context:
space:
mode:
authorochang <ochang@chromium.org>2016-01-12 19:42:10 -0800
committerCommit bot <commit-bot@chromium.org>2016-01-13 03:43:46 +0000
commitbd648ad6116ad3eb09356fb8c34fb006dbe86d4c (patch)
tree16ac668609a5e32a04e50990af810252357b864b /content/browser/media
parent245f6c4f3def6b1b8300f80caea7d41d8fafd5ad (diff)
downloadchromium_src-bd648ad6116ad3eb09356fb8c34fb006dbe86d4c.zip
chromium_src-bd648ad6116ad3eb09356fb8c34fb006dbe86d4c.tar.gz
chromium_src-bd648ad6116ad3eb09356fb8c34fb006dbe86d4c.tar.bz2
Prevent a race condition with MidiHost IPC sending.
EndSession() is moved from MidiHost's destructor into OnChannelClosing() before the destruction process starts (at which point it is unsafe to call any functions on the MidiHost/MidiManagerClient). Also moves a function call on a MidiManagerClient in MidiManager into the AutoLock scope. BUG=576383 R=toyoshim@chromium.org,agoode@chromium.org Review URL: https://codereview.chromium.org/1576323002 Cr-Commit-Position: refs/heads/master@{#369091}
Diffstat (limited to 'content/browser/media')
-rw-r--r--content/browser/media/midi_host.cc15
-rw-r--r--content/browser/media/midi_host.h1
2 files changed, 13 insertions, 3 deletions
diff --git a/content/browser/media/midi_host.cc b/content/browser/media/midi_host.cc
index 1e6de1e..30261ef 100644
--- a/content/browser/media/midi_host.cc
+++ b/content/browser/media/midi_host.cc
@@ -59,10 +59,19 @@ MidiHost::MidiHost(int renderer_process_id,
DCHECK(midi_manager_);
}
-MidiHost::~MidiHost() {
- // Close an open session, or abort opening a session.
- if (is_session_requested_ && midi_manager_)
+MidiHost::~MidiHost() = default;
+
+void MidiHost::OnChannelClosing() {
+ // If we get here the MidiHost is going to be destroyed soon. Prevent any
+ // subsequent calls from MidiManager by closing our session.
+ // If Send() is called from a different thread (e.g. a separate thread owned
+ // by the MidiManager implementation), it will get posted to the IO thread.
+ // There is a race condition here if our refcount is 0 and we're about to or
+ // have already entered OnDestruct().
+ if (is_session_requested_ && midi_manager_) {
midi_manager_->EndSession(this);
+ is_session_requested_ = false;
+ }
}
void MidiHost::OnDestruct() const {
diff --git a/content/browser/media/midi_host.h b/content/browser/media/midi_host.h
index 671bd3c..ca3706c 100644
--- a/content/browser/media/midi_host.h
+++ b/content/browser/media/midi_host.h
@@ -38,6 +38,7 @@ class CONTENT_EXPORT MidiHost : public BrowserMessageFilter,
MidiHost(int renderer_process_id, media::midi::MidiManager* midi_manager);
// BrowserMessageFilter implementation.
+ void OnChannelClosing() override;
void OnDestruct() const override;
bool OnMessageReceived(const IPC::Message& message) override;