From b2682c2cf5442bccae22ae4648b30f7f568444ff Mon Sep 17 00:00:00 2001
From: "robertshield@chromium.org"
 <robertshield@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>
Date: Mon, 2 Feb 2009 18:08:40 +0000
Subject: Setting the App Paths registry key at install time for admin users
 for chrome.exe.

URL=http://codereview.chromium.org/18560/show
BUG=5686


Review URL: http://codereview.chromium.org/19758

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@9046 0039d316-1c4b-4281-b951-d872f2087c98
---
 chrome/installer/util/shell_util.cc     | 29 +++++++++++++++++++++++++++++
 chrome/installer/util/shell_util.h      | 10 ++++++++++
 chrome/installer/util/util_constants.cc |  7 +++++++
 chrome/installer/util/util_constants.h  |  4 ++++
 4 files changed, 50 insertions(+)

(limited to 'chrome/installer/util')

diff --git a/chrome/installer/util/shell_util.cc b/chrome/installer/util/shell_util.cc
index 23bdc5a..7353f64 100644
--- a/chrome/installer/util/shell_util.cc
+++ b/chrome/installer/util/shell_util.cc
@@ -13,6 +13,7 @@
 
 #include "chrome/installer/util/shell_util.h"
 
+#include "base/file_path.h"
 #include "base/file_util.h"
 #include "base/logging.h"
 #include "base/path_service.h"
@@ -312,6 +313,11 @@ bool SetAccessDefaultRegEntries(HKEY root_key,
     delete (*itr);
   }
 
+  // Append the App Paths registry entries. Do this only if we are an admin,
+  // since they are always written to HKLM.
+  if (IsUserAnAdmin())
+    ShellUtil::AddChromeAppPathWorkItems(chrome_exe, items.get());
+
   // Apply all the registry changes and if there is a problem, rollback.
   if (!items->Do()) {
     LOG(ERROR) << "Failed to add Chrome to Set Program Access and Defaults";
@@ -465,6 +471,29 @@ bool ShellUtil::GetQuickLaunchPath(bool system_level, std::wstring* path) {
   return true;
 }
 
+void ShellUtil::AddChromeAppPathWorkItems(
+    const std::wstring& chrome_exe, WorkItemList* item_list) {
+  WorkItem* create_work_item = WorkItem::CreateCreateRegKeyWorkItem(
+      HKEY_LOCAL_MACHINE, installer_util::kAppPathsRegistryKey);
+
+  item_list->AddWorkItem(create_work_item);
+
+  WorkItem* set_default_value_work_item =
+      WorkItem::CreateSetRegValueWorkItem(HKEY_LOCAL_MACHINE,
+          installer_util::kAppPathsRegistryKey,
+          installer_util::kAppPathsRegistryDefaultName,
+          chrome_exe, true);
+  item_list->AddWorkItem(set_default_value_work_item);
+
+  FilePath chrome_path(chrome_exe);
+  WorkItem* set_path_value_work_item =
+      WorkItem::CreateSetRegValueWorkItem(HKEY_LOCAL_MACHINE,
+          installer_util::kAppPathsRegistryKey,
+          installer_util::kAppPathsRegistryPathName,
+          chrome_path.DirName().value(), true);
+  item_list->AddWorkItem(set_path_value_work_item);
+}
+
 bool ShellUtil::CreateChromeDesktopShortcut(const std::wstring& chrome_exe,
                                             int shell_change,
                                             bool create_new) {
diff --git a/chrome/installer/util/shell_util.h b/chrome/installer/util/shell_util.h
index a8f6beb..5f8300c 100644
--- a/chrome/installer/util/shell_util.h
+++ b/chrome/installer/util/shell_util.h
@@ -78,6 +78,15 @@ class ShellUtil {
   // Description of Chrome file/URL association handler ProgId.
   static const wchar_t* kChromeExtProgIdDesc;
 
+  // Populate work_item_list with WorkItem entries that will add chrome.exe to
+  // the set of App Paths registry keys so that ShellExecute can find it. Note
+  // that this is done in HKLM, regardless of whether this is a single-user
+  // install or not. For non-admin users, this will fail.
+  // chrome_exe: full path to chrome.exe
+  // work_item_list: pointer to the WorkItemList that will be populated
+  static void AddChromeAppPathWorkItems(const std::wstring& chrome_exe,
+                                        WorkItemList* work_item_list);
+
   // This method adds Chrome to the list that shows up in Add/Remove Programs->
   // Set Program Access and Defaults and also creates Chrome ProgIds under
   // Software\Classes. This method requires write access to HKLM so is just
@@ -188,6 +197,7 @@ class ShellUtil {
   static bool UpdateChromeShortcut(const std::wstring& chrome_exe,
                                    const std::wstring& shortcut,
                                    bool create_new);
+
  private:
   DISALLOW_EVIL_CONSTRUCTORS(ShellUtil);
 };
diff --git a/chrome/installer/util/util_constants.cc b/chrome/installer/util/util_constants.cc
index ab695e1..3fa7d21 100755
--- a/chrome/installer/util/util_constants.cc
+++ b/chrome/installer/util/util_constants.cc
@@ -79,6 +79,13 @@ const wchar_t kChromeDll[] = L"chrome.dll";
 const wchar_t kSetupExe[] = L"setup.exe";
 const wchar_t kInstallerDir[] = L"Installer";
 
+// Note that the following value must be kept in sync with kChromeExe
+const wchar_t kAppPathsRegistryKey[] =
+    L"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\App Paths\\chrome.exe";
+// Use the empty string to set the key default value.
+const wchar_t kAppPathsRegistryDefaultName[] = L"";
+const wchar_t kAppPathsRegistryPathName[] = L"Path";
+
 const wchar_t kUninstallStringField[] = L"UninstallString";
 const wchar_t kUninstallDisplayNameField[] = L"DisplayName";
 }  // namespace installer_util
diff --git a/chrome/installer/util/util_constants.h b/chrome/installer/util/util_constants.h
index aa2b27f..a8cbe9f 100755
--- a/chrome/installer/util/util_constants.h
+++ b/chrome/installer/util/util_constants.h
@@ -90,6 +90,10 @@ extern const wchar_t kChromeDll[];
 extern const wchar_t kSetupExe[];
 extern const wchar_t kInstallerDir[];
 
+extern const wchar_t kAppPathsRegistryKey[];
+extern const wchar_t kAppPathsRegistryDefaultName[];
+extern const wchar_t kAppPathsRegistryPathName[];
+
 extern const wchar_t kUninstallStringField[];
 extern const wchar_t kUninstallDisplayNameField[];
 }  // namespace installer_util
-- 
cgit v1.1