| Index: chrome_frame/ready_mode/internal/registry_ready_mode_state.cc
|
| ===================================================================
|
| --- chrome_frame/ready_mode/internal/registry_ready_mode_state.cc (revision 72310)
|
| +++ chrome_frame/ready_mode/internal/registry_ready_mode_state.cc (working copy)
|
| @@ -14,12 +14,13 @@
|
| #include "base/win/registry.h"
|
| #include "base/win/scoped_comptr.h"
|
| #include "base/win/scoped_handle.h"
|
| +#include "base/win/windows_version.h"
|
| #include "chrome/installer/util/browser_distribution.h"
|
| #include "chrome/installer/util/google_update_constants.h"
|
| #include "chrome/installer/util/master_preferences.h"
|
| #include "chrome/installer/util/util_constants.h"
|
| +#include "chrome_frame/chrome_launcher_utils.h"
|
| #include "chrome_frame/ready_mode/ready_mode.h"
|
| -#include "google_update_idl.h" // NOLINT
|
|
|
| namespace {
|
|
|
| @@ -53,28 +54,15 @@
|
| // the launched process, which the caller is responsible for closing, or NULL
|
| // upon failure.
|
| HANDLE LaunchCommandViaProcessLauncher(const std::wstring& command_field) {
|
| - BrowserDistribution* dist = BrowserDistribution::GetDistribution();
|
| + HANDLE launched_process = NULL;
|
|
|
| - base::win::ScopedComPtr<IProcessLauncher> ipl;
|
| - HRESULT hr = ipl.CreateInstance(__uuidof(ProcessLauncherClass));
|
| + scoped_ptr<CommandLine> command_line(
|
| + chrome_launcher::CreateUpdateCommandLine(command_field));
|
|
|
| - if (FAILED(hr)) {
|
| - DLOG(ERROR) << "Failed to instantiate IProcessLauncher: "
|
| - << base::StringPrintf("0x%08x", hr);
|
| - } else {
|
| - ULONG_PTR phandle = NULL;
|
| - DWORD id = GetCurrentProcessId();
|
| + if (command_line != NULL)
|
| + base::LaunchApp(*command_line, false, true, &launched_process);
|
|
|
| - hr = ipl->LaunchCmdElevated(dist->GetAppGuid().c_str(),
|
| - command_field.c_str(), id, &phandle);
|
| - if (SUCCEEDED(hr))
|
| - return reinterpret_cast<HANDLE>(phandle);
|
| -
|
| - DLOG(ERROR) << "Failed to invoke IProcessLauncher::LaunchCmdElevated: "
|
| - << base::StringPrintf("0x%08x", hr);
|
| - }
|
| -
|
| - return NULL;
|
| + return launched_process;
|
| }
|
|
|
| // Waits for the provided process to exit, and verifies that its exit code
|
| @@ -114,17 +102,34 @@
|
| return false;
|
| }
|
|
|
| +// If we are running on XP (no protected mode) or in a high-integrity process,
|
| +// we can invoke the installer directly. If not, we will have to go via the
|
| +// ProcessLauncher.
|
| +bool CanLaunchDirectly() {
|
| + if (base::win::GetVersion() < base::win::VERSION_VISTA)
|
| + return true;
|
| +
|
| + base::IntegrityLevel integrity_level = base::INTEGRITY_UNKNOWN;
|
| + if (!base::GetProcessIntegrityLevel(base::GetCurrentProcessHandle(),
|
| + &integrity_level)) {
|
| + DLOG(ERROR) << "Failed to determine process integrity level.";
|
| + return false;
|
| + }
|
| +
|
| + return integrity_level == base::HIGH_INTEGRITY;
|
| +}
|
| +
|
| // Attempts to launch the specified command either directly or via the
|
| // ProcessLauncher. Returns true if the command is launched and returns a
|
| // success code.
|
| bool LaunchAndCheckCommand(const std::wstring& command_field) {
|
| base::win::ScopedHandle handle;
|
|
|
| - handle.Set(LaunchCommandDirectly(command_field));
|
| - if (handle.IsValid() && CheckProcessExitCode(handle))
|
| - return true;
|
| + if (CanLaunchDirectly())
|
| + handle.Set(LaunchCommandDirectly(command_field));
|
| + else
|
| + handle.Set(LaunchCommandViaProcessLauncher(command_field));
|
|
|
| - handle.Set(LaunchCommandViaProcessLauncher(command_field));
|
| if (handle.IsValid() && CheckProcessExitCode(handle))
|
| return true;
|
|
|
|
|