Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(164)

Side by Side Diff: remoting/host/security_key/security_key_ipc_server_impl.cc

Issue 2478443002: Use ChannelMojo for remote security key channels. (Closed)
Patch Set: Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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/security_key/security_key_ipc_server_impl.h" 5 #include "remoting/host/security_key/security_key_ipc_server_impl.h"
6 6
7 #include <cstdint> 7 #include <cstdint>
8 #include <memory> 8 #include <memory>
9 #include <string> 9 #include <string>
10 10
11 #include "base/callback.h" 11 #include "base/callback.h"
12 #include "base/callback_helpers.h" 12 #include "base/callback_helpers.h"
13 #include "base/location.h" 13 #include "base/location.h"
14 #include "base/strings/utf_string_conversions.h"
14 #include "base/threading/thread_checker.h" 15 #include "base/threading/thread_checker.h"
15 #include "base/threading/thread_task_runner_handle.h" 16 #include "base/threading/thread_task_runner_handle.h"
16 #include "base/timer/timer.h" 17 #include "base/timer/timer.h"
17 #include "ipc/ipc_channel.h" 18 #include "ipc/ipc_channel.h"
18 #include "ipc/ipc_message.h" 19 #include "ipc/ipc_message.h"
19 #include "ipc/ipc_message_macros.h" 20 #include "ipc/ipc_message_macros.h"
21 #include "mojo/edk/embedder/embedder.h"
22 #include "mojo/edk/embedder/named_platform_handle.h"
23 #include "mojo/edk/embedder/named_platform_handle_utils.h"
20 #include "remoting/base/logging.h" 24 #include "remoting/base/logging.h"
21 #include "remoting/host/chromoting_messages.h" 25 #include "remoting/host/chromoting_messages.h"
22 #include "remoting/host/client_session_details.h" 26 #include "remoting/host/client_session_details.h"
23 27
24 #if defined(OS_WIN) 28 #if defined(OS_WIN)
25 #include "base/strings/stringprintf.h" 29 #include "base/strings/stringprintf.h"
26 #include "base/strings/utf_string_conversions.h" 30 #include "base/strings/utf_string_conversions.h"
27 #include "base/win/win_util.h" 31 #include "base/win/win_util.h"
28 #include "remoting/host/ipc_util.h" 32 #include "remoting/host/ipc_util.h"
29 #endif // defined(OS_WIN) 33 #endif // defined(OS_WIN)
30 34
31 namespace { 35 namespace {
32 36
33 // Returns the command code (the first byte of the data) if it exists, or -1 if 37 // Returns the command code (the first byte of the data) if it exists, or -1 if
34 // the data is empty. 38 // the data is empty.
35 unsigned int GetCommandCode(const std::string& data) { 39 unsigned int GetCommandCode(const std::string& data) {
36 return data.empty() ? -1 : static_cast<unsigned int>(data[0]); 40 return data.empty() ? -1 : static_cast<unsigned int>(data[0]);
37 } 41 }
38 42
39 } // namespace 43 } // namespace
40 44
41 namespace remoting { 45 namespace remoting {
42 46
43 SecurityKeyIpcServerImpl::SecurityKeyIpcServerImpl( 47 SecurityKeyIpcServerImpl::SecurityKeyIpcServerImpl(
44 int connection_id, 48 int connection_id,
45 ClientSessionDetails* client_session_details, 49 ClientSessionDetails* client_session_details,
46 base::TimeDelta initial_connect_timeout, 50 base::TimeDelta initial_connect_timeout,
47 const SecurityKeyAuthHandler::SendMessageCallback& message_callback, 51 const SecurityKeyAuthHandler::SendMessageCallback& message_callback,
52 const base::Closure& connect_callback,
48 const base::Closure& done_callback) 53 const base::Closure& done_callback)
49 : connection_id_(connection_id), 54 : connection_id_(connection_id),
50 client_session_details_(client_session_details), 55 client_session_details_(client_session_details),
51 initial_connect_timeout_(initial_connect_timeout), 56 initial_connect_timeout_(initial_connect_timeout),
57 connect_callback_(connect_callback),
52 done_callback_(done_callback), 58 done_callback_(done_callback),
53 message_callback_(message_callback), 59 message_callback_(message_callback),
54 weak_factory_(this) { 60 weak_factory_(this) {
55 DCHECK_GT(connection_id_, 0); 61 DCHECK_GT(connection_id_, 0);
56 DCHECK(!done_callback_.is_null()); 62 DCHECK(!done_callback_.is_null());
57 DCHECK(!message_callback_.is_null()); 63 DCHECK(!message_callback_.is_null());
58 } 64 }
59 65
60 SecurityKeyIpcServerImpl::~SecurityKeyIpcServerImpl() {} 66 SecurityKeyIpcServerImpl::~SecurityKeyIpcServerImpl() {
67 CloseChannel();
68 }
61 69
62 bool SecurityKeyIpcServerImpl::CreateChannel(const std::string& channel_name, 70 bool SecurityKeyIpcServerImpl::CreateChannel(
63 base::TimeDelta request_timeout) { 71 const mojo::edk::NamedPlatformHandle& channel_handle,
72 base::TimeDelta request_timeout) {
64 DCHECK(thread_checker_.CalledOnValidThread()); 73 DCHECK(thread_checker_.CalledOnValidThread());
65 DCHECK(!ipc_channel_); 74 DCHECK(!ipc_channel_);
66 security_key_request_timeout_ = request_timeout; 75 security_key_request_timeout_ = request_timeout;
67 76
77 mojo::edk::CreateServerHandleOptions options;
68 #if defined(OS_WIN) 78 #if defined(OS_WIN)
79 options.enforce_uniqueness = false;
69 // Create a named pipe owned by the current user (the LocalService account 80 // Create a named pipe owned by the current user (the LocalService account
70 // (SID: S-1-5-19) when running in the network process) which is available to 81 // (SID: S-1-5-19) when running in the network process) which is available to
71 // all authenticated users. 82 // all authenticated users.
72 // presubmit: allow wstring 83 // presubmit: allow wstring
73 std::wstring user_sid; 84 std::wstring user_sid;
74 if (!base::win::GetUserSidString(&user_sid)) { 85 if (!base::win::GetUserSidString(&user_sid)) {
75 return false; 86 return false;
76 } 87 }
77 std::string user_sid_utf8 = base::WideToUTF8(user_sid); 88 std::string user_sid_utf8 = base::WideToUTF8(user_sid);
78 std::string security_descriptor = base::StringPrintf( 89 options.security_descriptor = base::UTF8ToUTF16(base::StringPrintf(
79 "O:%sG:%sD:(A;;GA;;;AU)", user_sid_utf8.c_str(), user_sid_utf8.c_str()); 90 "O:%sG:%sD:(A;;GA;;;AU)", user_sid_utf8.c_str(), user_sid_utf8.c_str()));
80 91
81 base::win::ScopedHandle pipe; 92 #endif // defined(OS_WIN)
82 if (!CreateIpcChannel(channel_name, security_descriptor, &pipe)) { 93 mojo_peer_token_ = mojo::edk::GenerateRandomToken();
83 return false; 94 ipc_channel_ = IPC::Channel::CreateServer(
84 } 95 mojo::edk::ConnectToPeerProcess(
85 96 mojo::edk::CreateServerHandle(channel_handle, options),
86 ipc_channel_ = 97 mojo_peer_token_)
87 IPC::Channel::CreateNamedServer(IPC::ChannelHandle(pipe.Get()), this); 98 .release(),
88 #else // defined(OS_WIN) 99 this);
89 ipc_channel_ =
90 IPC::Channel::CreateNamedServer(IPC::ChannelHandle(channel_name), this);
91 #endif // !defined(OS_WIN)
92 100
93 if (!ipc_channel_->Connect()) { 101 if (!ipc_channel_->Connect()) {
94 ipc_channel_.reset(); 102 ipc_channel_.reset();
95 return false; 103 return false;
96 } 104 }
97 // It is safe to use base::Unretained here as |timer_| will be stopped and 105 // It is safe to use base::Unretained here as |timer_| will be stopped and
98 // this task will be removed when this instance is being destroyed. All 106 // this task will be removed when this instance is being destroyed. All
99 // methods must execute on the same thread (due to |thread_Checker_| so 107 // methods must execute on the same thread (due to |thread_Checker_| so
100 // the posted task and D'Tor can not execute concurrently. 108 // the posted task and D'Tor can not execute concurrently.
101 timer_.Start(FROM_HERE, initial_connect_timeout_, 109 timer_.Start(FROM_HERE, initial_connect_timeout_,
(...skipping 30 matching lines...) Expand all
132 IPC_MESSAGE_UNHANDLED(handled = false) 140 IPC_MESSAGE_UNHANDLED(handled = false)
133 IPC_END_MESSAGE_MAP() 141 IPC_END_MESSAGE_MAP()
134 142
135 CHECK(handled) << "Received unexpected IPC type: " << message.type(); 143 CHECK(handled) << "Received unexpected IPC type: " << message.type();
136 return handled; 144 return handled;
137 } 145 }
138 146
139 void SecurityKeyIpcServerImpl::OnChannelConnected(int32_t peer_pid) { 147 void SecurityKeyIpcServerImpl::OnChannelConnected(int32_t peer_pid) {
140 DCHECK(thread_checker_.CalledOnValidThread()); 148 DCHECK(thread_checker_.CalledOnValidThread());
141 149
150 if (!connect_callback_.is_null()) {
151 base::ResetAndReturn(&connect_callback_).Run();
152 }
153
142 #if defined(OS_WIN) 154 #if defined(OS_WIN)
143 DWORD peer_session_id; 155 DWORD peer_session_id;
144 if (!ProcessIdToSessionId(peer_pid, &peer_session_id)) { 156 if (!ProcessIdToSessionId(peer_pid, &peer_session_id)) {
145 PLOG(ERROR) << "ProcessIdToSessionId() failed"; 157 PLOG(ERROR) << "ProcessIdToSessionId() failed";
146 connection_close_pending_ = true; 158 connection_close_pending_ = true;
147 } else if (peer_session_id != client_session_details_->desktop_session_id()) { 159 } else if (peer_session_id != client_session_details_->desktop_session_id()) {
148 LOG(ERROR) << "Ignoring connection attempt from outside remoted session."; 160 LOG(ERROR) << "Ignoring connection attempt from outside remoted session.";
149 connection_close_pending_ = true; 161 connection_close_pending_ = true;
150 } 162 }
151 if (connection_close_pending_) { 163 if (connection_close_pending_) {
152 base::ThreadTaskRunnerHandle::Get()->PostTask( 164 base::ThreadTaskRunnerHandle::Get()->PostTask(
153 FROM_HERE, base::Bind(&SecurityKeyIpcServerImpl::OnChannelError, 165 FROM_HERE, base::Bind(&SecurityKeyIpcServerImpl::OnChannelError,
154 weak_factory_.GetWeakPtr())); 166 weak_factory_.GetWeakPtr()));
155 return; 167 return;
156 } 168 }
157 #else // !defined(OS_WIN) 169 #else // !defined(OS_WIN)
158 CHECK_EQ(client_session_details_->desktop_session_id(), UINT32_MAX); 170 CHECK_EQ(client_session_details_->desktop_session_id(), UINT32_MAX);
159 #endif // !defined(OS_WIN) 171 #endif // !defined(OS_WIN)
160 172
161 // Reset the timer to give the client a chance to send the request. 173 // Reset the timer to give the client a chance to send the request.
162 timer_.Start(FROM_HERE, initial_connect_timeout_, 174 timer_.Start(FROM_HERE, initial_connect_timeout_,
163 base::Bind(&SecurityKeyIpcServerImpl::OnChannelError, 175 base::Bind(&SecurityKeyIpcServerImpl::OnChannelError,
164 base::Unretained(this))); 176 base::Unretained(this)));
165 } 177 }
166 178
167 void SecurityKeyIpcServerImpl::OnChannelError() { 179 void SecurityKeyIpcServerImpl::OnChannelError() {
168 DCHECK(thread_checker_.CalledOnValidThread()); 180 DCHECK(thread_checker_.CalledOnValidThread());
169 if (ipc_channel_) { 181 CloseChannel();
170 ipc_channel_->Close(); 182
171 connection_close_pending_ = false; 183 if (!connect_callback_.is_null()) {
184 base::ResetAndReturn(&connect_callback_).Run();
172 } 185 }
173
174 if (!done_callback_.is_null()) { 186 if (!done_callback_.is_null()) {
175 // Note: This callback may result in this object being torn down. 187 // Note: This callback may result in this object being torn down.
176 base::ResetAndReturn(&done_callback_).Run(); 188 base::ResetAndReturn(&done_callback_).Run();
177 } 189 }
178 } 190 }
179 191
180 void SecurityKeyIpcServerImpl::OnSecurityKeyRequest( 192 void SecurityKeyIpcServerImpl::OnSecurityKeyRequest(
181 const std::string& request_data) { 193 const std::string& request_data) {
182 DCHECK(thread_checker_.CalledOnValidThread()); 194 DCHECK(thread_checker_.CalledOnValidThread());
183 195
184 // Reset the timer to give the client a chance to send the response. 196 // Reset the timer to give the client a chance to send the response.
185 timer_.Start(FROM_HERE, security_key_request_timeout_, 197 timer_.Start(FROM_HERE, security_key_request_timeout_,
186 base::Bind(&SecurityKeyIpcServerImpl::OnChannelError, 198 base::Bind(&SecurityKeyIpcServerImpl::OnChannelError,
187 base::Unretained(this))); 199 base::Unretained(this)));
188 200
189 HOST_LOG << "Received security key request: " << GetCommandCode(request_data); 201 HOST_LOG << "Received security key request: " << GetCommandCode(request_data);
190 message_callback_.Run(connection_id_, request_data); 202 message_callback_.Run(connection_id_, request_data);
191 } 203 }
192 204
205 void SecurityKeyIpcServerImpl::CloseChannel() {
206 if (ipc_channel_) {
207 ipc_channel_->Close();
208 connection_close_pending_ = false;
209 }
210 // Close the underlying mojo connection.
211 if (!mojo_peer_token_.empty()) {
212 mojo::edk::ClosePeerConnection(mojo_peer_token_);
213 mojo_peer_token_.clear();
214 }
215 }
216
193 } // namespace remoting 217 } // namespace remoting
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698