Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 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 "remoting/host/chromoting_host.h" | 5 #include "remoting/host/chromoting_host.h" |
| 6 | 6 |
| 7 #include "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/callback.h" | 8 #include "base/callback.h" |
| 9 #include "base/logging.h" | |
| 9 #include "build/build_config.h" | 10 #include "build/build_config.h" |
| 10 #include "remoting/base/constants.h" | 11 #include "remoting/base/constants.h" |
| 11 #include "remoting/base/encoder.h" | 12 #include "remoting/base/encoder.h" |
| 12 #include "remoting/base/encoder_row_based.h" | 13 #include "remoting/base/encoder_row_based.h" |
| 13 #include "remoting/base/encoder_vp8.h" | 14 #include "remoting/base/encoder_vp8.h" |
| 15 #include "remoting/base/logger.h" | |
| 14 #include "remoting/host/capturer.h" | 16 #include "remoting/host/capturer.h" |
| 15 #include "remoting/host/chromoting_host_context.h" | 17 #include "remoting/host/chromoting_host_context.h" |
| 16 #include "remoting/host/continue_window.h" | 18 #include "remoting/host/continue_window.h" |
| 17 #include "remoting/host/curtain.h" | 19 #include "remoting/host/curtain.h" |
| 18 #include "remoting/host/desktop_environment.h" | 20 #include "remoting/host/desktop_environment.h" |
| 19 #include "remoting/host/disconnect_window.h" | 21 #include "remoting/host/disconnect_window.h" |
| 20 #include "remoting/host/event_executor.h" | 22 #include "remoting/host/event_executor.h" |
| 21 #include "remoting/host/host_config.h" | 23 #include "remoting/host/host_config.h" |
| 22 #include "remoting/host/host_key_pair.h" | 24 #include "remoting/host/host_key_pair.h" |
| 23 #include "remoting/host/local_input_monitor.h" | 25 #include "remoting/host/local_input_monitor.h" |
| (...skipping 11 matching lines...) Expand all Loading... | |
| 35 using remoting::protocol::ConnectionToClient; | 37 using remoting::protocol::ConnectionToClient; |
| 36 using remoting::protocol::InputStub; | 38 using remoting::protocol::InputStub; |
| 37 | 39 |
| 38 static const int kContinueWindowTimeoutSecs = 5 * 60; | 40 static const int kContinueWindowTimeoutSecs = 5 * 60; |
| 39 | 41 |
| 40 namespace remoting { | 42 namespace remoting { |
| 41 | 43 |
| 42 // static | 44 // static |
| 43 ChromotingHost* ChromotingHost::Create(ChromotingHostContext* context, | 45 ChromotingHost* ChromotingHost::Create(ChromotingHostContext* context, |
| 44 MutableHostConfig* config, | 46 MutableHostConfig* config, |
| 45 AccessVerifier* access_verifier) { | 47 AccessVerifier* access_verifier, |
| 48 Logger* logger) { | |
| 46 Capturer* capturer = Capturer::Create(); | 49 Capturer* capturer = Capturer::Create(); |
| 47 EventExecutor* event_executor = | 50 EventExecutor* event_executor = |
| 48 EventExecutor::Create(context->desktop_message_loop(), capturer); | 51 EventExecutor::Create(context->desktop_message_loop(), capturer); |
| 49 Curtain* curtain = Curtain::Create(); | 52 Curtain* curtain = Curtain::Create(); |
| 50 DisconnectWindow* disconnect_window = DisconnectWindow::Create(); | 53 DisconnectWindow* disconnect_window = DisconnectWindow::Create(); |
| 51 ContinueWindow* continue_window = ContinueWindow::Create(); | 54 ContinueWindow* continue_window = ContinueWindow::Create(); |
| 52 LocalInputMonitor* local_input_monitor = LocalInputMonitor::Create(); | 55 LocalInputMonitor* local_input_monitor = LocalInputMonitor::Create(); |
| 53 return Create(context, config, | 56 return Create(context, config, |
| 54 new DesktopEnvironment(capturer, event_executor, curtain, | 57 new DesktopEnvironment(capturer, event_executor, curtain, |
| 55 disconnect_window, continue_window, | 58 disconnect_window, continue_window, |
| 56 local_input_monitor), | 59 local_input_monitor), |
| 57 access_verifier); | 60 access_verifier, logger); |
| 58 } | 61 } |
| 59 | 62 |
| 60 // static | 63 // static |
| 61 ChromotingHost* ChromotingHost::Create(ChromotingHostContext* context, | 64 ChromotingHost* ChromotingHost::Create(ChromotingHostContext* context, |
| 62 MutableHostConfig* config, | 65 MutableHostConfig* config, |
| 63 DesktopEnvironment* environment, | 66 DesktopEnvironment* environment, |
| 64 AccessVerifier* access_verifier) { | 67 AccessVerifier* access_verifier, |
| 65 return new ChromotingHost(context, config, environment, access_verifier); | 68 Logger* logger) { |
| 69 return new ChromotingHost(context, config, environment, access_verifier, | |
| 70 logger); | |
| 66 } | 71 } |
| 67 | 72 |
| 68 ChromotingHost::ChromotingHost(ChromotingHostContext* context, | 73 ChromotingHost::ChromotingHost(ChromotingHostContext* context, |
| 69 MutableHostConfig* config, | 74 MutableHostConfig* config, |
| 70 DesktopEnvironment* environment, | 75 DesktopEnvironment* environment, |
| 71 AccessVerifier* access_verifier) | 76 AccessVerifier* access_verifier, |
| 77 Logger* logger) | |
| 72 : context_(context), | 78 : context_(context), |
| 73 config_(config), | 79 config_(config), |
| 74 desktop_environment_(environment), | 80 desktop_environment_(environment), |
| 75 access_verifier_(access_verifier), | 81 access_verifier_(access_verifier), |
| 82 logger_(logger), | |
| 76 state_(kInitial), | 83 state_(kInitial), |
| 77 protocol_config_(protocol::CandidateSessionConfig::CreateDefault()), | 84 protocol_config_(protocol::CandidateSessionConfig::CreateDefault()), |
| 78 is_curtained_(false), | 85 is_curtained_(false), |
| 79 is_monitoring_local_inputs_(false), | 86 is_monitoring_local_inputs_(false), |
| 80 is_it2me_(false) { | 87 is_it2me_(false) { |
| 81 DCHECK(desktop_environment_.get()); | 88 DCHECK(desktop_environment_.get()); |
| 82 } | 89 } |
| 83 | 90 |
| 84 ChromotingHost::~ChromotingHost() { | 91 ChromotingHost::~ChromotingHost() { |
| 85 } | 92 } |
| 86 | 93 |
| 87 void ChromotingHost::Start() { | 94 void ChromotingHost::Start() { |
| 88 if (MessageLoop::current() != context_->main_message_loop()) { | 95 if (MessageLoop::current() != context_->main_message_loop()) { |
| 89 context_->main_message_loop()->PostTask( | 96 context_->main_message_loop()->PostTask( |
| 90 FROM_HERE, base::Bind(&ChromotingHost::Start, this)); | 97 FROM_HERE, base::Bind(&ChromotingHost::Start, this)); |
| 91 return; | 98 return; |
| 92 } | 99 } |
| 93 | 100 |
| 101 logger_->Log(logging::LOG_INFO, "Starting host"); | |
| 94 DCHECK(!jingle_client_); | 102 DCHECK(!jingle_client_); |
| 95 DCHECK(access_verifier_.get()); | 103 DCHECK(access_verifier_.get()); |
| 96 | 104 |
| 97 // Make sure this object is not started. | 105 // Make sure this object is not started. |
| 98 { | 106 { |
| 99 base::AutoLock auto_lock(lock_); | 107 base::AutoLock auto_lock(lock_); |
| 100 if (state_ != kInitial) | 108 if (state_ != kInitial) |
| 101 return; | 109 return; |
| 102 state_ = kStarted; | 110 state_ = kStarted; |
| 103 } | 111 } |
| 104 | 112 |
| 105 std::string xmpp_login; | 113 std::string xmpp_login; |
| 106 std::string xmpp_auth_token; | 114 std::string xmpp_auth_token; |
| 107 std::string xmpp_auth_service; | 115 std::string xmpp_auth_service; |
| 108 if (!config_->GetString(kXmppLoginConfigPath, &xmpp_login) || | 116 if (!config_->GetString(kXmppLoginConfigPath, &xmpp_login) || |
| 109 !config_->GetString(kXmppAuthTokenConfigPath, &xmpp_auth_token) || | 117 !config_->GetString(kXmppAuthTokenConfigPath, &xmpp_auth_token) || |
| 110 !config_->GetString(kXmppAuthServiceConfigPath, &xmpp_auth_service)) { | 118 !config_->GetString(kXmppAuthServiceConfigPath, &xmpp_auth_service)) { |
| 111 LOG(ERROR) << "XMPP credentials are not defined in the config."; | 119 logger_->Log(logging::LOG_ERROR, |
| 120 "XMPP credentials are not defined in the config."); | |
| 112 return; | 121 return; |
| 113 } | 122 } |
| 114 | 123 |
| 115 // Connect to the talk network with a JingleClient. | 124 // Connect to the talk network with a JingleClient. |
| 116 signal_strategy_.reset( | 125 signal_strategy_.reset( |
| 117 new XmppSignalStrategy(context_->jingle_thread(), xmpp_login, | 126 new XmppSignalStrategy(context_->jingle_thread(), xmpp_login, |
| 118 xmpp_auth_token, | 127 xmpp_auth_token, |
| 119 xmpp_auth_service)); | 128 xmpp_auth_service)); |
| 120 jingle_client_ = new JingleClient(context_->jingle_thread(), | 129 jingle_client_ = new JingleClient(context_->jingle_thread(), |
| 121 signal_strategy_.get(), | 130 signal_strategy_.get(), |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 174 | 183 |
| 175 void ChromotingHost::AddStatusObserver(HostStatusObserver* observer) { | 184 void ChromotingHost::AddStatusObserver(HostStatusObserver* observer) { |
| 176 DCHECK_EQ(state_, kInitial); | 185 DCHECK_EQ(state_, kInitial); |
| 177 status_observers_.push_back(observer); | 186 status_observers_.push_back(observer); |
| 178 } | 187 } |
| 179 | 188 |
| 180 //////////////////////////////////////////////////////////////////////////// | 189 //////////////////////////////////////////////////////////////////////////// |
| 181 // protocol::ConnectionToClient::EventHandler implementations | 190 // protocol::ConnectionToClient::EventHandler implementations |
| 182 void ChromotingHost::OnConnectionOpened(ConnectionToClient* connection) { | 191 void ChromotingHost::OnConnectionOpened(ConnectionToClient* connection) { |
| 183 DCHECK_EQ(context_->network_message_loop(), MessageLoop::current()); | 192 DCHECK_EQ(context_->network_message_loop(), MessageLoop::current()); |
| 184 VLOG(1) << "Connection to client established."; | 193 logger_->VLog(1, "Connection to client established."); |
| 185 // TODO(wez): ChromotingHost shouldn't need to know about Me2Mom. | 194 // TODO(wez): ChromotingHost shouldn't need to know about Me2Mom. |
| 186 if (is_it2me_) { | 195 if (is_it2me_) { |
| 187 context_->main_message_loop()->PostTask( | 196 context_->main_message_loop()->PostTask( |
| 188 FROM_HERE, base::Bind(&ChromotingHost::ProcessPreAuthentication, this, | 197 FROM_HERE, base::Bind(&ChromotingHost::ProcessPreAuthentication, this, |
| 189 make_scoped_refptr(connection))); | 198 make_scoped_refptr(connection))); |
| 190 } | 199 } |
| 191 } | 200 } |
| 192 | 201 |
| 193 void ChromotingHost::OnConnectionClosed(ConnectionToClient* connection) { | 202 void ChromotingHost::OnConnectionClosed(ConnectionToClient* connection) { |
| 194 DCHECK_EQ(context_->network_message_loop(), MessageLoop::current()); | 203 DCHECK_EQ(context_->network_message_loop(), MessageLoop::current()); |
| 195 | 204 |
| 196 VLOG(1) << "Connection to client closed."; | 205 logger_->VLog(1, "Connection to client closed."); |
| 197 context_->main_message_loop()->PostTask( | 206 context_->main_message_loop()->PostTask( |
| 198 FROM_HERE, base::Bind(&ChromotingHost::OnClientDisconnected, this, | 207 FROM_HERE, base::Bind(&ChromotingHost::OnClientDisconnected, this, |
| 199 make_scoped_refptr(connection))); | 208 make_scoped_refptr(connection))); |
| 200 } | 209 } |
| 201 | 210 |
| 202 void ChromotingHost::OnConnectionFailed(ConnectionToClient* connection) { | 211 void ChromotingHost::OnConnectionFailed(ConnectionToClient* connection) { |
| 203 DCHECK_EQ(context_->network_message_loop(), MessageLoop::current()); | 212 DCHECK_EQ(context_->network_message_loop(), MessageLoop::current()); |
| 204 | 213 |
| 205 LOG(ERROR) << "Connection failed unexpectedly."; | 214 logger_->Log(logging::LOG_ERROR, "Connection failed unexpectedly."); |
| 206 context_->main_message_loop()->PostTask( | 215 context_->main_message_loop()->PostTask( |
| 207 FROM_HERE, base::Bind(&ChromotingHost::OnClientDisconnected, this, | 216 FROM_HERE, base::Bind(&ChromotingHost::OnClientDisconnected, this, |
| 208 make_scoped_refptr(connection))); | 217 make_scoped_refptr(connection))); |
| 209 } | 218 } |
| 210 | 219 |
| 211 void ChromotingHost::OnSequenceNumberUpdated(ConnectionToClient* connection, | 220 void ChromotingHost::OnSequenceNumberUpdated(ConnectionToClient* connection, |
| 212 int64 sequence_number) { | 221 int64 sequence_number) { |
| 213 // Update the sequence number in ScreenRecorder. | 222 // Update the sequence number in ScreenRecorder. |
| 214 if (MessageLoop::current() != context_->main_message_loop()) { | 223 if (MessageLoop::current() != context_->main_message_loop()) { |
| 215 context_->main_message_loop()->PostTask( | 224 context_->main_message_loop()->PostTask( |
| 216 FROM_HERE, base::Bind(&ChromotingHost::OnSequenceNumberUpdated, this, | 225 FROM_HERE, base::Bind(&ChromotingHost::OnSequenceNumberUpdated, this, |
| 217 make_scoped_refptr(connection), sequence_number)); | 226 make_scoped_refptr(connection), sequence_number)); |
| 218 return; | 227 return; |
| 219 } | 228 } |
| 220 | 229 |
| 221 if (recorder_.get()) | 230 if (recorder_.get()) |
| 222 recorder_->UpdateSequenceNumber(sequence_number); | 231 recorder_->UpdateSequenceNumber(sequence_number); |
| 223 } | 232 } |
| 224 | 233 |
| 225 //////////////////////////////////////////////////////////////////////////// | 234 //////////////////////////////////////////////////////////////////////////// |
| 226 // JingleClient::Callback implementations | 235 // JingleClient::Callback implementations |
| 227 void ChromotingHost::OnStateChange(JingleClient* jingle_client, | 236 void ChromotingHost::OnStateChange(JingleClient* jingle_client, |
| 228 JingleClient::State state) { | 237 JingleClient::State state) { |
| 229 DCHECK_EQ(MessageLoop::current(), context_->network_message_loop()); | 238 DCHECK_EQ(MessageLoop::current(), context_->network_message_loop()); |
| 230 | 239 |
| 231 if (state == JingleClient::CONNECTED) { | 240 if (state == JingleClient::CONNECTED) { |
| 232 std::string jid = jingle_client->GetFullJid(); | 241 std::string jid = jingle_client->GetFullJid(); |
| 233 | 242 |
| 234 DCHECK_EQ(jingle_client_.get(), jingle_client); | 243 DCHECK_EQ(jingle_client_.get(), jingle_client); |
| 235 VLOG(1) << "Host connected as " << jid; | 244 logger_->Log(logging::LOG_INFO, "Host connected as %s", jid.c_str()); |
| 236 | 245 |
| 237 // Create and start session manager. | 246 // Create and start session manager. |
| 238 protocol::JingleSessionManager* server = | 247 protocol::JingleSessionManager* server = |
| 239 new protocol::JingleSessionManager(context_->jingle_thread()); | 248 new protocol::JingleSessionManager(context_->jingle_thread()); |
| 240 // TODO(ajwong): Make this a command switch when we're more stable. | 249 // TODO(ajwong): Make this a command switch when we're more stable. |
| 241 server->set_allow_local_ips(true); | 250 server->set_allow_local_ips(true); |
| 242 | 251 |
| 243 // Assign key and certificate to server. | 252 // Assign key and certificate to server. |
| 244 HostKeyPair key_pair; | 253 HostKeyPair key_pair; |
| 245 CHECK(key_pair.Load(config_)) | 254 CHECK(key_pair.Load(config_)) |
| 246 << "Failed to load server authentication data"; | 255 << "Failed to load server authentication data"; |
| 247 | 256 |
| 248 server->Init(jid, jingle_client->session_manager(), | 257 server->Init(jid, jingle_client->session_manager(), |
| 249 NewCallback(this, &ChromotingHost::OnNewClientSession), | 258 NewCallback(this, &ChromotingHost::OnNewClientSession), |
| 250 key_pair.CopyPrivateKey(), key_pair.GenerateCertificate()); | 259 key_pair.CopyPrivateKey(), key_pair.GenerateCertificate()); |
| 251 | 260 |
| 252 session_manager_ = server; | 261 session_manager_ = server; |
| 253 | 262 |
| 254 for (StatusObserverList::iterator it = status_observers_.begin(); | 263 for (StatusObserverList::iterator it = status_observers_.begin(); |
| 255 it != status_observers_.end(); ++it) { | 264 it != status_observers_.end(); ++it) { |
| 256 (*it)->OnSignallingConnected(signal_strategy_.get(), jid); | 265 (*it)->OnSignallingConnected(signal_strategy_.get(), jid); |
| 257 } | 266 } |
| 258 } else if (state == JingleClient::CLOSED) { | 267 } else if (state == JingleClient::CLOSED) { |
| 259 VLOG(1) << "Host disconnected from talk network."; | 268 logger_->Log(logging::LOG_INFO, "Host disconnected from talk network."); |
|
dmac
2011/06/26 14:34:44
why did we change this from a vlog?
garykac
2011/06/27 21:24:20
Because this is info that I want to see in the UI
| |
| 260 for (StatusObserverList::iterator it = status_observers_.begin(); | 269 for (StatusObserverList::iterator it = status_observers_.begin(); |
| 261 it != status_observers_.end(); ++it) { | 270 it != status_observers_.end(); ++it) { |
| 262 (*it)->OnSignallingDisconnected(); | 271 (*it)->OnSignallingDisconnected(); |
| 263 } | 272 } |
| 264 // TODO(sergeyu): Don't shutdown the host and let the upper level | 273 // TODO(sergeyu): Don't shutdown the host and let the upper level |
| 265 // decide what needs to be done when signalling channel is | 274 // decide what needs to be done when signalling channel is |
| 266 // disconnected. | 275 // disconnected. |
| 267 Shutdown(NULL); | 276 Shutdown(NULL); |
| 268 } | 277 } |
| 269 } | 278 } |
| (...skipping 29 matching lines...) Expand all Loading... | |
| 299 | 308 |
| 300 // TODO(simonmorris): The resolution is set in the video stream now, | 309 // TODO(simonmorris): The resolution is set in the video stream now, |
| 301 // so it doesn't need to be set here. | 310 // so it doesn't need to be set here. |
| 302 *protocol_config_->mutable_initial_resolution() = | 311 *protocol_config_->mutable_initial_resolution() = |
| 303 protocol::ScreenResolution(2048, 2048); | 312 protocol::ScreenResolution(2048, 2048); |
| 304 // TODO(sergeyu): Respect resolution requested by the client if supported. | 313 // TODO(sergeyu): Respect resolution requested by the client if supported. |
| 305 protocol::SessionConfig* config = protocol_config_->Select( | 314 protocol::SessionConfig* config = protocol_config_->Select( |
| 306 session->candidate_config(), true /* force_host_resolution */); | 315 session->candidate_config(), true /* force_host_resolution */); |
| 307 | 316 |
| 308 if (!config) { | 317 if (!config) { |
| 309 LOG(WARNING) << "Rejecting connection from " << session->jid() | 318 logger_->Log(logging::LOG_WARNING, |
| 310 << " because no compatible configuration has been found."; | 319 "Rejecting connection from %s because no compatible" |
| 320 " configuration has been found.", session->jid().c_str()); | |
| 311 *response = protocol::SessionManager::INCOMPATIBLE; | 321 *response = protocol::SessionManager::INCOMPATIBLE; |
| 312 return; | 322 return; |
| 313 } | 323 } |
| 314 | 324 |
| 315 session->set_config(config); | 325 session->set_config(config); |
| 316 session->set_receiver_token( | 326 session->set_receiver_token( |
| 317 GenerateHostAuthToken(session->initiator_token())); | 327 GenerateHostAuthToken(session->initiator_token())); |
| 318 | 328 |
| 319 *response = protocol::SessionManager::ACCEPT; | 329 *response = protocol::SessionManager::ACCEPT; |
| 320 | 330 |
| 321 VLOG(1) << "Client connected: " << session->jid(); | 331 logger_->Log(logging::LOG_INFO, "Client connected: %s", |
|
dmac
2011/06/26 14:34:44
we did we change from a vlog?
garykac
2011/06/27 21:24:20
As above.
| |
| 332 session->jid().c_str()); | |
| 322 | 333 |
| 323 // We accept the connection, so create a connection object. | 334 // We accept the connection, so create a connection object. |
| 324 ConnectionToClient* connection = new ConnectionToClient( | 335 ConnectionToClient* connection = new ConnectionToClient( |
| 325 context_->network_message_loop(), this); | 336 context_->network_message_loop(), this); |
| 326 | 337 |
| 327 // Create a client object. | 338 // Create a client object. |
| 328 ClientSession* client = new ClientSession( | 339 ClientSession* client = new ClientSession( |
| 329 this, | 340 this, |
| 330 UserAuthenticator::Create(), | 341 UserAuthenticator::Create(), |
| 331 connection, | 342 connection, |
| (...skipping 363 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 695 | 706 |
| 696 for (std::vector<Task*>::iterator it = shutdown_tasks_.begin(); | 707 for (std::vector<Task*>::iterator it = shutdown_tasks_.begin(); |
| 697 it != shutdown_tasks_.end(); ++it) { | 708 it != shutdown_tasks_.end(); ++it) { |
| 698 (*it)->Run(); | 709 (*it)->Run(); |
| 699 delete *it; | 710 delete *it; |
| 700 } | 711 } |
| 701 shutdown_tasks_.clear(); | 712 shutdown_tasks_.clear(); |
| 702 } | 713 } |
| 703 | 714 |
| 704 } // namespace remoting | 715 } // namespace remoting |
| OLD | NEW |