diff options
author | satish@chromium.org <satish@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-01-20 15:27:16 +0000 |
---|---|---|
committer | satish@chromium.org <satish@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-01-20 15:27:16 +0000 |
commit | 9dc1c1a6bc8f0342ca262d3002269f34642923d3 (patch) | |
tree | e0cc80f9276e3843fe7fcce4cc25b92521bf0692 /chrome/browser/speech | |
parent | 2f7aa5e70b39ffc61ce637e3f1f0138278e98d1f (diff) | |
download | chromium_src-9dc1c1a6bc8f0342ca262d3002269f34642923d3.zip chromium_src-9dc1c1a6bc8f0342ca262d3002269f34642923d3.tar.gz chromium_src-9dc1c1a6bc8f0342ca262d3002269f34642923d3.tar.bz2 |
Cancel any pending speech recognitions when the dispatcher host terminates.
I have not added a new test for this because the existing test is flaky and
didn't seem right to add another flaky test like that. Instead I've added a TODO
to add a browser test for this case once the flaky test has been fixed.
BUG=none
TEST=manual
Review URL: http://codereview.chromium.org/6358007
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@71956 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/speech')
-rw-r--r-- | chrome/browser/speech/speech_input_browsertest.cc | 28 | ||||
-rw-r--r-- | chrome/browser/speech/speech_input_dispatcher_host.cc | 11 | ||||
-rw-r--r-- | chrome/browser/speech/speech_input_dispatcher_host.h | 1 | ||||
-rw-r--r-- | chrome/browser/speech/speech_input_manager.cc | 16 | ||||
-rw-r--r-- | chrome/browser/speech/speech_input_manager.h | 2 |
5 files changed, 47 insertions, 11 deletions
diff --git a/chrome/browser/speech/speech_input_browsertest.cc b/chrome/browser/speech/speech_input_browsertest.cc index e0b2aff..45b41be 100644 --- a/chrome/browser/speech/speech_input_browsertest.cc +++ b/chrome/browser/speech/speech_input_browsertest.cc @@ -42,14 +42,14 @@ class FakeSpeechInputManager : public SpeechInputManager { } // SpeechInputManager methods. - void StartRecognition(Delegate* delegate, - int caller_id, - int render_process_id, - int render_view_id, - const gfx::Rect& element_rect, - const std::string& language, - const std::string& grammar, - const std::string& origin_url) { + virtual void StartRecognition(Delegate* delegate, + int caller_id, + int render_process_id, + int render_view_id, + const gfx::Rect& element_rect, + const std::string& language, + const std::string& grammar, + const std::string& origin_url) { VLOG(1) << "StartRecognition invoked."; EXPECT_EQ(0, caller_id_); EXPECT_EQ(NULL, delegate_); @@ -60,17 +60,20 @@ class FakeSpeechInputManager : public SpeechInputManager { MessageLoop::current()->PostTask(FROM_HERE, NewRunnableMethod(this, &FakeSpeechInputManager::SetFakeRecognitionResult)); } - void CancelRecognition(int caller_id) { + virtual void CancelRecognition(int caller_id) { VLOG(1) << "CancelRecognition invoked."; EXPECT_EQ(caller_id_, caller_id); caller_id_ = 0; delegate_ = NULL; } - void StopRecording(int caller_id) { + virtual void StopRecording(int caller_id) { VLOG(1) << "StopRecording invoked."; EXPECT_EQ(caller_id_, caller_id); // Nothing to do here since we aren't really recording. } + virtual void CancelAllRequestsWithDelegate(Delegate* delegate) { + VLOG(1) << "CancelAllRequestsWithDelegate invoked."; + } private: void SetFakeRecognitionResult() { @@ -167,6 +170,11 @@ SpeechInputManager* SpeechInputBrowserTest::speech_input_manager_ = NULL; // check for sending many clicks in succession to the speech button and verify // that it doesn't cause any crash but works as expected. This should act as the // test for http://crbug.com/59173 +// +// TODO(satish): Similar to above, once this flakiness has been fixed add +// another test here to check that when speech recognition is in progress and +// a renderer crashes, we get a call to +// SpeechInputManager::CancelAllRequestsWithDelegate. #if defined(OS_WIN) #define MAYBE_TestBasicRecognition FLAKY_TestBasicRecognition #else diff --git a/chrome/browser/speech/speech_input_dispatcher_host.cc b/chrome/browser/speech/speech_input_dispatcher_host.cc index cfcbed7..dc993d5 100644 --- a/chrome/browser/speech/speech_input_dispatcher_host.cc +++ b/chrome/browser/speech/speech_input_dispatcher_host.cc @@ -105,13 +105,21 @@ SpeechInputManager::AccessorMethod* SpeechInputDispatcherHost::manager_accessor_ = &SpeechInputManager::Get; SpeechInputDispatcherHost::SpeechInputDispatcherHost(int render_process_id) - : render_process_id_(render_process_id) { + : render_process_id_(render_process_id), + may_have_pending_requests_(false) { // This is initialized by Browser. Do not add any non-trivial // initialization here, instead do it lazily when required (e.g. see the // method |manager()|) or add an Init() method. } SpeechInputDispatcherHost::~SpeechInputDispatcherHost() { + // If the renderer crashed for some reason or if we didn't receive a proper + // Cancel/Stop call for an existing session, cancel such active sessions now. + // We first check if this dispatcher received any speech IPC requst so that + // we don't end up creating the speech input manager for web pages which don't + // use speech input. + if (may_have_pending_requests_) + manager()->CancelAllRequestsWithDelegate(this); } SpeechInputManager* SpeechInputDispatcherHost::manager() { @@ -131,6 +139,7 @@ bool SpeechInputDispatcherHost::OnMessageReceived( return true; } + may_have_pending_requests_ = true; IPC_BEGIN_MESSAGE_MAP_EX(SpeechInputDispatcherHost, message, *message_was_ok) IPC_MESSAGE_HANDLER(SpeechInputHostMsg_StartRecognition, diff --git a/chrome/browser/speech/speech_input_dispatcher_host.h b/chrome/browser/speech/speech_input_dispatcher_host.h index d8befd3..23a1f23 100644 --- a/chrome/browser/speech/speech_input_dispatcher_host.h +++ b/chrome/browser/speech/speech_input_dispatcher_host.h @@ -51,6 +51,7 @@ class SpeechInputDispatcherHost : public BrowserMessageFilter, SpeechInputManager* manager(); int render_process_id_; + bool may_have_pending_requests_; // Set if we received any speech IPC request static SpeechInputManager::AccessorMethod* manager_accessor_; diff --git a/chrome/browser/speech/speech_input_manager.cc b/chrome/browser/speech/speech_input_manager.cc index f59a3b7..56a87c9 100644 --- a/chrome/browser/speech/speech_input_manager.cc +++ b/chrome/browser/speech/speech_input_manager.cc @@ -111,6 +111,8 @@ class SpeechInputManagerImpl : public SpeechInputManager, const std::string& origin_url); virtual void CancelRecognition(int caller_id); virtual void StopRecording(int caller_id); + virtual void CancelAllRequestsWithDelegate( + SpeechInputManagerDelegate* delegate); // SpeechRecognizer::Delegate methods. virtual void SetRecognitionResult(int caller_id, @@ -265,6 +267,20 @@ void SpeechInputManagerImpl::CancelRecognition(int caller_id) { bubble_controller_->CloseBubble(caller_id); } +void SpeechInputManagerImpl::CancelAllRequestsWithDelegate( + SpeechInputManagerDelegate* delegate) { + SpeechRecognizerMap::iterator it = requests_.begin(); + while (it != requests_.end()) { + if (it->second.delegate == delegate) { + CancelRecognition(it->first); + // This map will have very few elements so it is simpler to restart. + it = requests_.begin(); + } else { + ++it; + } + } +} + void SpeechInputManagerImpl::StopRecording(int caller_id) { DCHECK(HasPendingRequest(caller_id)); requests_[caller_id].recognizer->StopRecording(); diff --git a/chrome/browser/speech/speech_input_manager.h b/chrome/browser/speech/speech_input_manager.h index 83bde90..2c607ad 100644 --- a/chrome/browser/speech/speech_input_manager.h +++ b/chrome/browser/speech/speech_input_manager.h @@ -63,6 +63,8 @@ class SpeechInputManager { const std::string& origin_url) = 0; virtual void CancelRecognition(int caller_id) = 0; virtual void StopRecording(int caller_id) = 0; + + virtual void CancelAllRequestsWithDelegate(Delegate* delegate) = 0; }; // This typedef is to workaround the issue with certain versions of |