Chromium Code Reviews| Index: chrome/browser/automation/testing_automation_provider.cc |
| diff --git a/chrome/browser/automation/testing_automation_provider.cc b/chrome/browser/automation/testing_automation_provider.cc |
| index 58a04741f2109e7b289ffce7f17fd92bf98a8d0e..4f40946edfc0f95a236ab28dcdd872ae7c9a6583 100644 |
| --- a/chrome/browser/automation/testing_automation_provider.cc |
| +++ b/chrome/browser/automation/testing_automation_provider.cc |
| @@ -20,6 +20,7 @@ |
| #include "base/process.h" |
| #include "base/process_util.h" |
| #include "base/stringprintf.h" |
| +#include "base/synchronization/waitable_event.h" |
| #include "base/threading/thread_restrictions.h" |
| #include "base/time.h" |
| #include "base/utf_string_conversions.h" |
| @@ -176,6 +177,24 @@ class AutomationInterstitialPage : public InterstitialPage { |
| DISALLOW_COPY_AND_ASSIGN(AutomationInterstitialPage); |
| }; |
| +// Waits for all currently pending tasks on |identifier| to be processed before |
| +// returning. Returns false if |identifier| is the current thread, or a task |
| +// could not be posted. Returns true otherwise. |
| +bool WaitForPendingTasksOn(BrowserThread::ID identifier) { |
| + // Avoid deadlocking self. |
| + if (BrowserThread::CurrentlyOn(identifier)) |
| + return false; |
| + base::WaitableEvent event(true, // manual reset |
| + false); // not initially signaled |
| + if (!BrowserThread::PostTask( |
| + identifier, |
| + FROM_HERE, |
| + base::Bind(&base::WaitableEvent::Signal, base::Unretained(&event)))) |
| + return false; |
| + event.Wait(); |
|
Paweł Hajdan Jr.
2011/10/19 09:20:02
I think this also returns bool, so please return e
|
| + return true; |
| +} |
| + |
| } // namespace |
| TestingAutomationProvider::TestingAutomationProvider(Profile* profile) |
| @@ -2734,12 +2753,10 @@ namespace { |
| // Used by AutomationProvider::GetBrowserInfo(). |
| class GetChildProcessHostInfoTask : public Task { |
| public: |
| - GetChildProcessHostInfoTask(base::WaitableEvent* event, |
| - ListValue* child_processes) |
| - : event_(event), |
| - child_processes_(child_processes) {} |
| + explicit GetChildProcessHostInfoTask(ListValue* child_processes) |
| + : child_processes_(child_processes) {} |
| - virtual void Run() { |
| + virtual void Run() OVERRIDE { |
| DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); |
| for (BrowserChildProcessHost::Iterator iter; !iter.Done(); ++iter) { |
| // Only add processes which are already started, |
| @@ -2755,11 +2772,9 @@ class GetChildProcessHostInfoTask : public Task { |
| item->SetInteger("pid", base::GetProcId(info->handle())); |
| child_processes_->Append(item); |
| } |
| - event_->Signal(); |
| } |
| private: |
| - base::WaitableEvent* const event_; // weak |
| ListValue* child_processes_; |
| DISALLOW_COPY_AND_ASSIGN(GetChildProcessHostInfoTask); |
| @@ -2881,12 +2896,10 @@ void TestingAutomationProvider::GetBrowserInfo( |
| // Add all child processes in a list of dictionaries, one dictionary item |
| // per child process. |
| ListValue* child_processes = new ListValue; |
| - base::WaitableEvent event(true /* manual reset */, |
| - false /* not initially signaled */); |
| CHECK(BrowserThread::PostTask( |
| BrowserThread::IO, FROM_HERE, |
| - new GetChildProcessHostInfoTask(&event, child_processes))); |
| - event.Wait(); |
| + new GetChildProcessHostInfoTask(child_processes))); |
| + CHECK(WaitForPendingTasksOn(BrowserThread::IO)); |
|
jam
2011/10/19 23:56:27
instead of blocking one thread on another, why not
|
| return_value->Set("child_processes", child_processes); |
| // Add all extension processes in a list of dictionaries, one dictionary |
| @@ -5901,6 +5914,14 @@ void TestingAutomationProvider::SetPolicies( |
| } |
| } |
| + // OverridePolicies() triggers preference updates, which triggers preference |
| + // listeners. Some policies (e.g. URLBlacklist) post tasks to other message |
| + // loops before they start being enforced; make sure those tasks have |
| + // finished. |
| + CHECK(WaitForPendingTasksOn(BrowserThread::IO)); |
|
jam
2011/10/19 23:56:27
ditto
|
| + CHECK(WaitForPendingTasksOn(BrowserThread::FILE)); |
| + CHECK(WaitForPendingTasksOn(BrowserThread::IO)); |
| + |
| reply.SendSuccess(NULL); |
| #endif // defined(OFFICIAL_BUILD) |
| } |