| OLD | NEW | 
|    1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |    1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 
|    2 // Use of this source code is governed by a BSD-style license that can be |    2 // Use of this source code is governed by a BSD-style license that can be | 
|    3 // found in the LICENSE file. |    3 // found in the LICENSE file. | 
|    4  |    4  | 
|    5 #include "content/browser/utility_process_host_impl.h" |    5 #include "content/browser/utility_process_host_impl.h" | 
|    6  |    6  | 
|    7 #include "base/bind.h" |    7 #include "base/bind.h" | 
|    8 #include "base/bind_helpers.h" |    8 #include "base/bind_helpers.h" | 
|    9 #include "base/command_line.h" |    9 #include "base/command_line.h" | 
|   10 #include "base/lazy_instance.h" |   10 #include "base/lazy_instance.h" | 
|   11 #include "base/message_loop/message_loop.h" |   11 #include "base/message_loop/message_loop.h" | 
|   12 #include "base/run_loop.h" |   12 #include "base/run_loop.h" | 
|   13 #include "base/sequenced_task_runner.h" |   13 #include "base/sequenced_task_runner.h" | 
|   14 #include "base/strings/utf_string_conversions.h" |   14 #include "base/strings/utf_string_conversions.h" | 
|   15 #include "base/synchronization/lock.h" |   15 #include "base/synchronization/lock.h" | 
|   16 #include "base/synchronization/waitable_event.h" |   16 #include "base/synchronization/waitable_event.h" | 
|   17 #include "content/browser/browser_child_process_host_impl.h" |   17 #include "content/browser/browser_child_process_host_impl.h" | 
|   18 #include "content/browser/renderer_host/render_process_host_impl.h" |   18 #include "content/browser/renderer_host/render_process_host_impl.h" | 
|   19 #include "content/child/child_process.h" |  | 
|   20 #include "content/common/child_process_host_impl.h" |   19 #include "content/common/child_process_host_impl.h" | 
|   21 #include "content/common/utility_messages.h" |   20 #include "content/common/utility_messages.h" | 
|   22 #include "content/public/browser/browser_thread.h" |   21 #include "content/public/browser/browser_thread.h" | 
|   23 #include "content/public/browser/content_browser_client.h" |   22 #include "content/public/browser/content_browser_client.h" | 
|   24 #include "content/public/browser/utility_process_host_client.h" |   23 #include "content/public/browser/utility_process_host_client.h" | 
|   25 #include "content/public/common/content_switches.h" |   24 #include "content/public/common/content_switches.h" | 
|   26 #include "content/public/common/process_type.h" |   25 #include "content/public/common/process_type.h" | 
|   27 #include "content/utility/utility_thread_impl.h" |  | 
|   28 #include "ipc/ipc_switches.h" |   26 #include "ipc/ipc_switches.h" | 
|   29 #include "ui/base/ui_base_switches.h" |   27 #include "ui/base/ui_base_switches.h" | 
|   30  |   28  | 
|   31 #if defined(OS_WIN) |   29 #if defined(OS_WIN) | 
|   32 #include "content/public/common/sandboxed_process_launcher_delegate.h" |   30 #include "content/public/common/sandboxed_process_launcher_delegate.h" | 
|   33 #endif |   31 #endif | 
|   34  |   32  | 
|   35 namespace content { |   33 namespace content { | 
|   36  |   34  | 
|   37 #if defined(OS_WIN) |   35 #if defined(OS_WIN) | 
|   38 // NOTE: changes to this class need to be reviewed by the security team. |   36 // NOTE: changes to this class need to be reviewed by the security team. | 
|   39 class UtilitySandboxedProcessLauncherDelegate |   37 class UtilitySandboxedProcessLauncherDelegate | 
|   40     : public SandboxedProcessLauncherDelegate { |   38     : public SandboxedProcessLauncherDelegate { | 
|   41  public: |   39  public: | 
|   42   explicit UtilitySandboxedProcessLauncherDelegate( |   40   explicit UtilitySandboxedProcessLauncherDelegate( | 
|   43     const base::FilePath& exposed_dir) : exposed_dir_(exposed_dir) {} |   41     const base::FilePath& exposed_dir) : exposed_dir_(exposed_dir) {} | 
|   44   virtual ~UtilitySandboxedProcessLauncherDelegate() {} |   42   virtual ~UtilitySandboxedProcessLauncherDelegate() {} | 
|   45  |   43  | 
|   46   virtual void PreSandbox(bool* disable_default_policy, |   44   virtual void PreSandbox(bool* disable_default_policy, | 
|   47                           base::FilePath* exposed_dir) OVERRIDE { |   45                           base::FilePath* exposed_dir) OVERRIDE { | 
|   48     *exposed_dir = exposed_dir_; |   46     *exposed_dir = exposed_dir_; | 
|   49   } |   47   } | 
|   50  |   48  | 
|   51 private: |   49 private: | 
|   52   base::FilePath exposed_dir_; |   50   base::FilePath exposed_dir_; | 
|   53 }; |   51 }; | 
|   54 #endif |   52 #endif | 
|   55  |   53  | 
|   56 // We want to ensure there's only one utility thread running at a time, as there |  | 
|   57 // are many globals used in the utility process. |  | 
|   58 static base::LazyInstance<base::Lock> g_one_utility_thread_lock; |  | 
|   59  |   54  | 
|   60 // Single process not supported in multiple dll mode currently. |   55 UtilityMainThreadFactoryFunction g_utility_main_thread_factory = NULL; | 
|   61 #if !defined(CHROME_MULTIPLE_DLL) |  | 
|   62 class UtilityMainThread : public base::Thread { |  | 
|   63  public: |  | 
|   64   UtilityMainThread(const std::string& channel_id) |  | 
|   65       : Thread("Chrome_InProcUtilityThread"), |  | 
|   66         channel_id_(channel_id) { |  | 
|   67   } |  | 
|   68  |  | 
|   69   virtual ~UtilityMainThread() { |  | 
|   70     Stop(); |  | 
|   71   } |  | 
|   72  |  | 
|   73  private: |  | 
|   74   // base::Thread implementation: |  | 
|   75   virtual void Init() OVERRIDE { |  | 
|   76     // We need to return right away or else the main thread that started us will |  | 
|   77     // hang. |  | 
|   78     base::MessageLoop::current()->PostTask( |  | 
|   79         FROM_HERE, |  | 
|   80         base::Bind(&UtilityMainThread::InitInternal, base::Unretained(this))); |  | 
|   81   } |  | 
|   82  |  | 
|   83   virtual void CleanUp() OVERRIDE { |  | 
|   84     child_process_.reset(); |  | 
|   85  |  | 
|   86     // See comment in RendererMainThread. |  | 
|   87     SetThreadWasQuitProperly(true); |  | 
|   88     g_one_utility_thread_lock.Get().Release(); |  | 
|   89   } |  | 
|   90  |  | 
|   91   void InitInternal() { |  | 
|   92     g_one_utility_thread_lock.Get().Acquire(); |  | 
|   93     child_process_.reset(new ChildProcess()); |  | 
|   94     child_process_->set_main_thread(new UtilityThreadImpl(channel_id_)); |  | 
|   95   } |  | 
|   96  |  | 
|   97   std::string channel_id_; |  | 
|   98   scoped_ptr<ChildProcess> child_process_; |  | 
|   99  |  | 
|  100   DISALLOW_COPY_AND_ASSIGN(UtilityMainThread); |  | 
|  101 }; |  | 
|  102 #endif  // !CHROME_MULTIPLE_DLL |  | 
|  103  |   56  | 
|  104 UtilityProcessHost* UtilityProcessHost::Create( |   57 UtilityProcessHost* UtilityProcessHost::Create( | 
|  105     UtilityProcessHostClient* client, |   58     UtilityProcessHostClient* client, | 
|  106     base::SequencedTaskRunner* client_task_runner) { |   59     base::SequencedTaskRunner* client_task_runner) { | 
|  107   return new UtilityProcessHostImpl(client, client_task_runner); |   60   return new UtilityProcessHostImpl(client, client_task_runner); | 
|  108 } |   61 } | 
|  109  |   62  | 
 |   63 void UtilityProcessHost::RegisterUtilityMainThreadFactory( | 
 |   64     UtilityMainThreadFactoryFunction create) { | 
 |   65   g_utility_main_thread_factory = create; | 
 |   66 } | 
 |   67  | 
|  110 UtilityProcessHostImpl::UtilityProcessHostImpl( |   68 UtilityProcessHostImpl::UtilityProcessHostImpl( | 
|  111     UtilityProcessHostClient* client, |   69     UtilityProcessHostClient* client, | 
|  112     base::SequencedTaskRunner* client_task_runner) |   70     base::SequencedTaskRunner* client_task_runner) | 
|  113     : client_(client), |   71     : client_(client), | 
|  114       client_task_runner_(client_task_runner), |   72       client_task_runner_(client_task_runner), | 
|  115       is_batch_mode_(false), |   73       is_batch_mode_(false), | 
|  116       is_mdns_enabled_(false), |   74       is_mdns_enabled_(false), | 
|  117       no_sandbox_(false), |   75       no_sandbox_(false), | 
|  118 #if defined(OS_LINUX) |   76 #if defined(OS_LINUX) | 
|  119       child_flags_(ChildProcessHost::CHILD_ALLOW_SELF), |   77       child_flags_(ChildProcessHost::CHILD_ALLOW_SELF), | 
| (...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  189   // Name must be set or metrics_service will crash in any test which |  147   // Name must be set or metrics_service will crash in any test which | 
|  190   // launches a UtilityProcessHost. |  148   // launches a UtilityProcessHost. | 
|  191   process_.reset(new BrowserChildProcessHostImpl(PROCESS_TYPE_UTILITY, this)); |  149   process_.reset(new BrowserChildProcessHostImpl(PROCESS_TYPE_UTILITY, this)); | 
|  192   process_->SetName(ASCIIToUTF16("utility process")); |  150   process_->SetName(ASCIIToUTF16("utility process")); | 
|  193  |  151  | 
|  194   std::string channel_id = process_->GetHost()->CreateChannel(); |  152   std::string channel_id = process_->GetHost()->CreateChannel(); | 
|  195   if (channel_id.empty()) |  153   if (channel_id.empty()) | 
|  196     return false; |  154     return false; | 
|  197  |  155  | 
|  198   // Single process not supported in multiple dll mode currently. |  156   // Single process not supported in multiple dll mode currently. | 
|  199 #if !defined(CHROME_MULTIPLE_DLL) |  157   if (RenderProcessHost::run_renderer_in_process() && | 
|  200   if (RenderProcessHost::run_renderer_in_process()) { |  158       g_utility_main_thread_factory) { | 
|  201     // See comment in RenderProcessHostImpl::Init() for the background on why we |  159     // See comment in RenderProcessHostImpl::Init() for the background on why we | 
|  202     // support single process mode this way. |  160     // support single process mode this way. | 
|  203     in_process_thread_.reset(new UtilityMainThread(channel_id)); |  161     in_process_thread_.reset(g_utility_main_thread_factory(channel_id)); | 
|  204     in_process_thread_->Start(); |  162     in_process_thread_->Start(); | 
|  205   } else |  163   } else { | 
|  206 #endif  // !CHROME_MULTIPLE_DLL |  | 
|  207   { |  | 
|  208     const CommandLine& browser_command_line = *CommandLine::ForCurrentProcess(); |  164     const CommandLine& browser_command_line = *CommandLine::ForCurrentProcess(); | 
|  209     int child_flags = child_flags_; |  165     int child_flags = child_flags_; | 
|  210  |  166  | 
|  211 #if defined(OS_POSIX) |  167 #if defined(OS_POSIX) | 
|  212     bool has_cmd_prefix = browser_command_line.HasSwitch( |  168     bool has_cmd_prefix = browser_command_line.HasSwitch( | 
|  213         switches::kUtilityCmdPrefix); |  169         switches::kUtilityCmdPrefix); | 
|  214  |  170  | 
|  215     // When running under gdb, forking /proc/self/exe ends up forking the gdb |  171     // When running under gdb, forking /proc/self/exe ends up forking the gdb | 
|  216     // executable instead of Chromium. It is almost safe to assume that no |  172     // executable instead of Chromium. It is almost safe to assume that no | 
|  217     // updates will happen while a developer is running with |  173     // updates will happen while a developer is running with | 
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  288 } |  244 } | 
|  289  |  245  | 
|  290 void UtilityProcessHostImpl::OnProcessCrashed(int exit_code) { |  246 void UtilityProcessHostImpl::OnProcessCrashed(int exit_code) { | 
|  291   client_task_runner_->PostTask( |  247   client_task_runner_->PostTask( | 
|  292       FROM_HERE, |  248       FROM_HERE, | 
|  293       base::Bind(&UtilityProcessHostClient::OnProcessCrashed, client_.get(), |  249       base::Bind(&UtilityProcessHostClient::OnProcessCrashed, client_.get(), | 
|  294             exit_code)); |  250             exit_code)); | 
|  295 } |  251 } | 
|  296  |  252  | 
|  297 }  // namespace content |  253 }  // namespace content | 
| OLD | NEW |