[email protected] | 6241ac6 | 2012-09-12 22:12:38 | [diff] [blame] | 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 |
| 3 | // found in the LICENSE file. |
| 4 | // |
| 5 | // This file implements the Windows service controlling Me2Me host processes |
| 6 | // running within user sessions. |
| 7 | |
| 8 | #include "remoting/host/desktop_process.h" |
| 9 | |
[email protected] | 12066cb | 2012-10-25 03:25:43 | [diff] [blame] | 10 | #include "base/bind.h" |
| 11 | #include "base/bind_helpers.h" |
| 12 | #include "base/logging.h" |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 13 | #include "base/memory/ref_counted.h" |
| 14 | #include "base/message_loop.h" |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 15 | #include "ipc/ipc_channel_proxy.h" |
| 16 | #include "remoting/base/auto_thread.h" |
| 17 | #include "remoting/base/auto_thread_task_runner.h" |
[email protected] | 12066cb | 2012-10-25 03:25:43 | [diff] [blame] | 18 | #include "remoting/host/chromoting_messages.h" |
| 19 | #include "remoting/host/desktop_session_agent.h" |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 20 | |
[email protected] | 6241ac6 | 2012-09-12 22:12:38 | [diff] [blame] | 21 | namespace remoting { |
| 22 | |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 23 | DesktopProcess::DesktopProcess( |
| 24 | scoped_refptr<AutoThreadTaskRunner> caller_task_runner, |
| 25 | const std::string& daemon_channel_name) |
| 26 | : caller_task_runner_(caller_task_runner), |
| 27 | daemon_channel_name_(daemon_channel_name) { |
| 28 | DCHECK(caller_task_runner_->BelongsToCurrentThread()); |
| 29 | DCHECK_EQ(MessageLoop::current()->type(), MessageLoop::TYPE_UI); |
[email protected] | 6241ac6 | 2012-09-12 22:12:38 | [diff] [blame] | 30 | } |
| 31 | |
| 32 | DesktopProcess::~DesktopProcess() { |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 33 | DCHECK(!daemon_channel_); |
| 34 | DCHECK(!desktop_agent_); |
[email protected] | 6241ac6 | 2012-09-12 22:12:38 | [diff] [blame] | 35 | } |
| 36 | |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 37 | bool DesktopProcess::OnMessageReceived(const IPC::Message& message) { |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 38 | DCHECK(caller_task_runner_->BelongsToCurrentThread()); |
| 39 | |
[email protected] | 12066cb | 2012-10-25 03:25:43 | [diff] [blame] | 40 | bool handled = true; |
| 41 | IPC_BEGIN_MESSAGE_MAP(DesktopProcess, message) |
| 42 | IPC_MESSAGE_HANDLER(ChromotingDaemonDesktopMsg_Crash, OnCrash) |
| 43 | IPC_MESSAGE_UNHANDLED(handled = false) |
| 44 | IPC_END_MESSAGE_MAP() |
| 45 | return handled; |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 46 | } |
| 47 | |
| 48 | void DesktopProcess::OnChannelConnected(int32 peer_pid) { |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 49 | DCHECK(caller_task_runner_->BelongsToCurrentThread()); |
| 50 | |
[email protected] | 12066cb | 2012-10-25 03:25:43 | [diff] [blame] | 51 | VLOG(1) << "IPC: desktop <- daemon (" << peer_pid << ")"; |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 52 | } |
| 53 | |
| 54 | void DesktopProcess::OnChannelError() { |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 55 | DCHECK(caller_task_runner_->BelongsToCurrentThread()); |
| 56 | |
[email protected] | 12066cb | 2012-10-25 03:25:43 | [diff] [blame] | 57 | // Shutdown the desktop process. |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 58 | daemon_channel_.reset(); |
[email protected] | ff72dd1 | 2012-11-27 05:18:25 | [diff] [blame] | 59 | desktop_agent_->Stop(); |
| 60 | desktop_agent_ = NULL; |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 61 | caller_task_runner_ = NULL; |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 62 | } |
| 63 | |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 64 | bool DesktopProcess::Start() { |
| 65 | DCHECK(caller_task_runner_->BelongsToCurrentThread()); |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 66 | |
[email protected] | 31014af | 2012-11-30 04:04:57 | [diff] [blame^] | 67 | // Launch the input thread. |
| 68 | scoped_refptr<AutoThreadTaskRunner> input_task_runner = |
| 69 | AutoThread::CreateWithType("Input thread", caller_task_runner_, |
| 70 | MessageLoop::TYPE_IO); |
| 71 | |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 72 | // Launch the I/O thread. |
| 73 | scoped_refptr<AutoThreadTaskRunner> io_task_runner = |
[email protected] | ff72dd1 | 2012-11-27 05:18:25 | [diff] [blame] | 74 | AutoThread::CreateWithType("I/O thread", caller_task_runner_, |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 75 | MessageLoop::TYPE_IO); |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 76 | |
[email protected] | ff72dd1 | 2012-11-27 05:18:25 | [diff] [blame] | 77 | // Launch the video capture thread. |
| 78 | scoped_refptr<AutoThreadTaskRunner> video_capture_task_runner = |
| 79 | AutoThread::Create("Video capture thread", caller_task_runner_); |
| 80 | |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 81 | // Create a desktop agent. |
| 82 | desktop_agent_ = DesktopSessionAgent::Create(caller_task_runner_, |
[email protected] | 31014af | 2012-11-30 04:04:57 | [diff] [blame^] | 83 | input_task_runner, |
[email protected] | ff72dd1 | 2012-11-27 05:18:25 | [diff] [blame] | 84 | io_task_runner, |
| 85 | video_capture_task_runner); |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 86 | |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 87 | // Start the agent and create an IPC channel to talk to it. It is safe to |
| 88 | // use base::Unretained(this) here because the message loop below will run |
| 89 | // until |desktop_agent_| is completely destroyed. |
| 90 | IPC::PlatformFileForTransit desktop_pipe; |
| 91 | if (!desktop_agent_->Start(base::Bind(&DesktopProcess::OnChannelError, |
| 92 | base::Unretained(this)), |
| 93 | &desktop_pipe)) { |
[email protected] | ff72dd1 | 2012-11-27 05:18:25 | [diff] [blame] | 94 | desktop_agent_ = NULL; |
| 95 | caller_task_runner_ = NULL; |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 96 | return false; |
[email protected] | 09fb5e7 | 2012-10-18 07:15:19 | [diff] [blame] | 97 | } |
| 98 | |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 99 | // Connect to the daemon. |
| 100 | daemon_channel_.reset(new IPC::ChannelProxy(daemon_channel_name_, |
| 101 | IPC::Channel::MODE_CLIENT, |
| 102 | this, |
| 103 | io_task_runner)); |
[email protected] | 12066cb | 2012-10-25 03:25:43 | [diff] [blame] | 104 | |
[email protected] | 2b51d74 | 2012-10-26 02:07:27 | [diff] [blame] | 105 | // Pass |desktop_pipe| to the daemon. |
| 106 | daemon_channel_->Send( |
| 107 | new ChromotingDesktopDaemonMsg_DesktopAttached(desktop_pipe)); |
| 108 | |
| 109 | return true; |
[email protected] | 12066cb | 2012-10-25 03:25:43 | [diff] [blame] | 110 | } |
| 111 | |
| 112 | void DesktopProcess::OnCrash(const std::string& function_name, |
| 113 | const std::string& file_name, |
| 114 | const int& line_number) { |
| 115 | // The daemon requested us to crash the process. |
| 116 | CHECK(false); |
[email protected] | 6241ac6 | 2012-09-12 22:12:38 | [diff] [blame] | 117 | } |
| 118 | |
| 119 | } // namespace remoting |