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

Side by Side Diff: remoting/host/win/launch_process_with_token.cc

Issue 11118005: Pass the client end handle of the network-to-daemon IPC channel via handle inheritance. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 8 years, 2 months 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 | Annotate | Revision Log
OLDNEW
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 "remoting/host/win/launch_process_with_token.h" 5 #include "remoting/host/win/launch_process_with_token.h"
6 6
7 #include <windows.h> 7 #include <windows.h>
8 #include <sddl.h>
8 #include <winternl.h> 9 #include <winternl.h>
9 10
11 #include <limits>
12
10 #include "base/logging.h" 13 #include "base/logging.h"
11 #include "base/memory/scoped_ptr.h" 14 #include "base/memory/scoped_ptr.h"
15 #include "base/process_util.h"
16 #include "base/rand_util.h"
12 #include "base/scoped_native_library.h" 17 #include "base/scoped_native_library.h"
18 #include "base/single_thread_task_runner.h"
13 #include "base/stringprintf.h" 19 #include "base/stringprintf.h"
14 #include "base/utf_string_conversions.h" 20 #include "base/utf_string_conversions.h"
15 #include "base/win/scoped_handle.h" 21 #include "base/win/scoped_handle.h"
16 #include "base/win/scoped_process_information.h" 22 #include "base/win/scoped_process_information.h"
17 #include "base/win/windows_version.h" 23 #include "base/win/windows_version.h"
24 #include "ipc/ipc_channel_proxy.h"
18 25
19 using base::win::ScopedHandle; 26 using base::win::ScopedHandle;
20 27
21 namespace { 28 namespace {
22 29
30 // Match the pipe name prefix used by Chrome IPC channels so that the client
31 // could use Chrome IPC APIs instead of connecting manually.
32 const char kChromePipeNamePrefix[] = "\\\\.\\pipe\\chrome.";
33
23 const char kCreateProcessDefaultPipeNameFormat[] = 34 const char kCreateProcessDefaultPipeNameFormat[] =
24 "\\\\.\\Pipe\\TerminalServer\\SystemExecSrvr\\%d"; 35 "\\\\.\\Pipe\\TerminalServer\\SystemExecSrvr\\%d";
25 36
26 // Undocumented WINSTATIONINFOCLASS value causing 37 // Undocumented WINSTATIONINFOCLASS value causing
27 // winsta!WinStationQueryInformationW() to return the name of the pipe for 38 // winsta!WinStationQueryInformationW() to return the name of the pipe for
28 // requesting cross-session process creation. 39 // requesting cross-session process creation.
29 const WINSTATIONINFOCLASS kCreateProcessPipeNameClass = 40 const WINSTATIONINFOCLASS kCreateProcessPipeNameClass =
30 static_cast<WINSTATIONINFOCLASS>(0x21); 41 static_cast<WINSTATIONINFOCLASS>(0x21);
31 42
32 const int kPipeBusyWaitTimeoutMs = 2000; 43 const int kPipeBusyWaitTimeoutMs = 2000;
(...skipping 359 matching lines...) Expand 10 before | Expand all | Expand 10 after
392 } 403 }
393 404
394 *process_information_out = process_information; 405 *process_information_out = process_information;
395 return true; 406 return true;
396 } 407 }
397 408
398 } // namespace 409 } // namespace
399 410
400 namespace remoting { 411 namespace remoting {
401 412
413 bool CreateIpcChannel(
414 const std::string& channel_name,
415 const std::string& pipe_security_descriptor,
416 scoped_refptr<base::SingleThreadTaskRunner> io_task_runner,
417 IPC::Listener* delegate,
418 scoped_ptr<IPC::ChannelProxy>* channel_out) {
419 // Create security descriptor for the channel.
420 SECURITY_ATTRIBUTES security_attributes;
421 security_attributes.nLength = sizeof(security_attributes);
422 security_attributes.bInheritHandle = FALSE;
423
424 ULONG security_descriptor_length = 0;
425 if (!ConvertStringSecurityDescriptorToSecurityDescriptor(
426 UTF8ToUTF16(pipe_security_descriptor).c_str(),
427 SDDL_REVISION_1,
428 reinterpret_cast<PSECURITY_DESCRIPTOR*>(
429 &security_attributes.lpSecurityDescriptor),
430 &security_descriptor_length)) {
431 LOG_GETLASTERROR(ERROR) <<
432 "Failed to create a security descriptor for the Chromoting IPC channel";
433 return false;
434 }
435
436 // Convert the channel name to the pipe name.
437 std::string pipe_name(kChromePipeNamePrefix);
438 pipe_name.append(channel_name);
439
440 // Create the server end of the pipe. This code should match the code in
441 // IPC::Channel with exception of passing a non-default security descriptor.
442 base::win::ScopedHandle pipe;
443 pipe.Set(CreateNamedPipe(
444 UTF8ToUTF16(pipe_name).c_str(),
445 PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED | FILE_FLAG_FIRST_PIPE_INSTANCE,
446 PIPE_TYPE_BYTE | PIPE_READMODE_BYTE,
447 1,
448 IPC::Channel::kReadBufferSize,
449 IPC::Channel::kReadBufferSize,
450 5000,
451 &security_attributes));
452 if (!pipe.IsValid()) {
453 LOG_GETLASTERROR(ERROR) <<
454 "Failed to create the server end of the Chromoting IPC channel";
455 LocalFree(security_attributes.lpSecurityDescriptor);
456 return false;
457 }
458
459 LocalFree(security_attributes.lpSecurityDescriptor);
460
461 // Wrap the pipe into an IPC channel.
462 channel_out->reset(new IPC::ChannelProxy(
463 IPC::ChannelHandle(pipe),
464 IPC::Channel::MODE_SERVER,
465 delegate,
466 io_task_runner));
467 return true;
468 }
469
402 // Creates a copy of the current process token for the given |session_id| so 470 // Creates a copy of the current process token for the given |session_id| so
403 // it can be used to launch a process in that session. 471 // it can be used to launch a process in that session.
404 bool CreateSessionToken(uint32 session_id, ScopedHandle* token_out) { 472 bool CreateSessionToken(uint32 session_id, ScopedHandle* token_out) {
405 ScopedHandle session_token; 473 ScopedHandle session_token;
406 DWORD desired_access = TOKEN_ADJUST_DEFAULT | TOKEN_ADJUST_SESSIONID | 474 DWORD desired_access = TOKEN_ADJUST_DEFAULT | TOKEN_ADJUST_SESSIONID |
407 TOKEN_ASSIGN_PRIMARY | TOKEN_DUPLICATE | TOKEN_QUERY; 475 TOKEN_ASSIGN_PRIMARY | TOKEN_DUPLICATE | TOKEN_QUERY;
408 if (!CopyProcessToken(desired_access, &session_token)) { 476 if (!CopyProcessToken(desired_access, &session_token)) {
409 return false; 477 return false;
410 } 478 }
411 479
(...skipping 22 matching lines...) Expand all
434 return false; 502 return false;
435 } 503 }
436 504
437 // Revert to the default token. 505 // Revert to the default token.
438 CHECK(RevertToSelf()); 506 CHECK(RevertToSelf());
439 507
440 *token_out = session_token.Pass(); 508 *token_out = session_token.Pass();
441 return true; 509 return true;
442 } 510 }
443 511
512 // Generates a unique IPC channel name.
513 std::string GenerateIpcChannelName(void* client) {
514 // Generate the pipe name. This code is copied from
515 // src/content/common/child_process_host_impl.cc
516 return base::StringPrintf("%d.%p.%d",
517 base::GetCurrentProcId(), client,
518 base::RandInt(0, std::numeric_limits<int>::max()));
519 }
520
444 bool LaunchProcessWithToken(const FilePath& binary, 521 bool LaunchProcessWithToken(const FilePath& binary,
445 const CommandLine::StringType& command_line, 522 const CommandLine::StringType& command_line,
446 HANDLE user_token, 523 HANDLE user_token,
524 bool inherit_handles,
447 DWORD creation_flags, 525 DWORD creation_flags,
448 ScopedHandle* process_out, 526 ScopedHandle* process_out,
449 ScopedHandle* thread_out) { 527 ScopedHandle* thread_out) {
450 FilePath::StringType application_name = binary.value(); 528 FilePath::StringType application_name = binary.value();
451 529
452 base::win::ScopedProcessInformation process_info; 530 base::win::ScopedProcessInformation process_info;
453 STARTUPINFOW startup_info; 531 STARTUPINFOW startup_info;
454 532
455 string16 desktop_name(UTF8ToUTF16(kDefaultDesktopName)); 533 string16 desktop_name(UTF8ToUTF16(kDefaultDesktopName));
456 534
457 memset(&startup_info, 0, sizeof(startup_info)); 535 memset(&startup_info, 0, sizeof(startup_info));
458 startup_info.cb = sizeof(startup_info); 536 startup_info.cb = sizeof(startup_info);
459 startup_info.lpDesktop = const_cast<char16*>(desktop_name.c_str()); 537 startup_info.lpDesktop = const_cast<char16*>(desktop_name.c_str());
460 538
461 BOOL result = CreateProcessAsUser(user_token, 539 BOOL result = CreateProcessAsUser(user_token,
462 application_name.c_str(), 540 application_name.c_str(),
463 const_cast<LPWSTR>(command_line.c_str()), 541 const_cast<LPWSTR>(command_line.c_str()),
464 NULL, 542 NULL,
465 NULL, 543 NULL,
466 FALSE, 544 inherit_handles,
467 creation_flags, 545 creation_flags,
468 NULL, 546 NULL,
469 NULL, 547 NULL,
470 &startup_info, 548 &startup_info,
471 process_info.Receive()); 549 process_info.Receive());
472 550
473 // CreateProcessAsUser will fail on XP and W2K3 with ERROR_PIPE_NOT_CONNECTED 551 // CreateProcessAsUser will fail on XP and W2K3 with ERROR_PIPE_NOT_CONNECTED
474 // if the user hasn't logged to the target session yet. In such a case 552 // if the user hasn't logged to the target session yet. In such a case
475 // we try to talk to the execution server directly emulating what 553 // we try to talk to the execution server directly emulating what
476 // the undocumented and not-exported advapi32!CreateRemoteSessionProcessW() 554 // the undocumented and not-exported advapi32!CreateRemoteSessionProcessW()
(...skipping 28 matching lines...) Expand all
505 return false; 583 return false;
506 } 584 }
507 585
508 CHECK(process_info.IsValid()); 586 CHECK(process_info.IsValid());
509 process_out->Set(process_info.TakeProcessHandle()); 587 process_out->Set(process_info.TakeProcessHandle());
510 thread_out->Set(process_info.TakeThreadHandle()); 588 thread_out->Set(process_info.TakeThreadHandle());
511 return true; 589 return true;
512 } 590 }
513 591
514 } // namespace remoting 592 } // namespace remoting
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698