summaryrefslogtreecommitdiffstats
path: root/media/midi/midi_manager.cc
diff options
context:
space:
mode:
authortoyoshim <toyoshim@chromium.org>2014-10-23 00:17:59 -0700
committerCommit bot <commit-bot@chromium.org>2014-10-23 07:18:17 +0000
commit71fcb150d9e2cb5e2f05069177ac611ac9c189c0 (patch)
tree5067da853f0f8b7d7b52a0fb632ad93e33701fe7 /media/midi/midi_manager.cc
parent7a0ddbb2ced7ed2117ae177773714968f66a66b5 (diff)
downloadchromium_src-71fcb150d9e2cb5e2f05069177ac611ac9c189c0.zip
chromium_src-71fcb150d9e2cb5e2f05069177ac611ac9c189c0.tar.gz
chromium_src-71fcb150d9e2cb5e2f05069177ac611ac9c189c0.tar.bz2
Manage MIDI related objects and sessions' lifecycles correctly
Following changes are needed to maintain MIDIPortInfoList contents consistent in each MidiMessageFilter instances when MidiManager update the list asynchronously. Essential changes: - Call EndSession iff a session is open. - Do not use client_id to communicate between browser and renderer. Multiple clients are managed in a MidiMessageFilter existing in each renderer. Minor changes: - Remove midi_manager_ checks in MIDIHost, and add CHECK insteads. - Rename MidiManagerFilter::StartSession to MidiManagerFilter::AddClient to be aligned with RemoveClient. A session can be shared with multiple clients. After this change, MidiManager::EndSession is called from each Renderer and RendererHost at the right timing, e.g., GC collects the last MIDIAccess reference in JavaScript. See, also http://crbug.com/424859. BUG=424859 Review URL: https://codereview.chromium.org/662853003 Cr-Commit-Position: refs/heads/master@{#300851}
Diffstat (limited to 'media/midi/midi_manager.cc')
-rw-r--r--media/midi/midi_manager.cc28
1 files changed, 17 insertions, 11 deletions
diff --git a/media/midi/midi_manager.cc b/media/midi/midi_manager.cc
index c53eef4..b0439ec 100644
--- a/media/midi/midi_manager.cc
+++ b/media/midi/midi_manager.cc
@@ -26,7 +26,7 @@ MidiManager* MidiManager::Create() {
}
#endif
-void MidiManager::StartSession(MidiManagerClient* client, int client_id) {
+void MidiManager::StartSession(MidiManagerClient* client) {
bool session_is_ready;
bool session_needs_initialization = false;
bool too_many_pending_clients_exist = false;
@@ -34,6 +34,12 @@ void MidiManager::StartSession(MidiManagerClient* client, int client_id) {
{
base::AutoLock auto_lock(lock_);
session_is_ready = initialized_;
+ if (clients_.find(client) != clients_.end() ||
+ pending_clients_.find(client) != pending_clients_.end()) {
+ // Should not happen. But just in case the renderer is compromised.
+ NOTREACHED();
+ return;
+ }
if (!session_is_ready) {
// Do not accept a new request if the pending client list contains too
// many clients.
@@ -43,7 +49,7 @@ void MidiManager::StartSession(MidiManagerClient* client, int client_id) {
if (!too_many_pending_clients_exist) {
// Call StartInitialization() only for the first request.
session_needs_initialization = pending_clients_.empty();
- pending_clients_.insert(std::make_pair(client, client_id));
+ pending_clients_.insert(client);
}
}
}
@@ -58,7 +64,7 @@ void MidiManager::StartSession(MidiManagerClient* client, int client_id) {
}
if (too_many_pending_clients_exist) {
// Return an error immediately if there are too many requests.
- client->CompleteStartSession(client_id, MIDI_INITIALIZATION_ERROR);
+ client->CompleteStartSession(MIDI_INITIALIZATION_ERROR);
return;
}
// CompleteInitialization() will be called asynchronously when platform
@@ -75,10 +81,12 @@ void MidiManager::StartSession(MidiManagerClient* client, int client_id) {
clients_.insert(client);
result = result_;
}
- client->CompleteStartSession(client_id, result);
+ client->CompleteStartSession(result);
}
void MidiManager::EndSession(MidiManagerClient* client) {
+ // At this point, |client| can be in the destruction process, and calling
+ // any method of |client| is dangerous.
base::AutoLock auto_lock(lock_);
clients_.erase(client);
pending_clients_.erase(client);
@@ -121,8 +129,8 @@ void MidiManager::ReceiveMidiData(
double timestamp) {
base::AutoLock auto_lock(lock_);
- for (ClientList::iterator i = clients_.begin(); i != clients_.end(); ++i)
- (*i)->ReceiveMidiData(port_index, data, length, timestamp);
+ for (MidiManagerClient* client : clients_)
+ client->ReceiveMidiData(port_index, data, length, timestamp);
}
void MidiManager::CompleteInitializationInternal(MidiResult result) {
@@ -134,12 +142,10 @@ void MidiManager::CompleteInitializationInternal(MidiResult result) {
initialized_ = true;
result_ = result;
- for (PendingClientMap::iterator it = pending_clients_.begin();
- it != pending_clients_.end();
- ++it) {
+ for (MidiManagerClient* client : pending_clients_) {
if (result_ == MIDI_OK)
- clients_.insert(it->first);
- it->first->CompleteStartSession(it->second, result_);
+ clients_.insert(client);
+ client->CompleteStartSession(result_);
}
pending_clients_.clear();
}