| OLD | NEW |
| 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 "chrome/installer/setup/setup_main.h" | 5 #include "chrome/installer/setup/setup_main.h" |
| 6 | 6 |
| 7 #include <windows.h> | 7 #include <windows.h> |
| 8 #include <msi.h> | 8 #include <msi.h> |
| 9 #include <shellapi.h> | 9 #include <shellapi.h> |
| 10 #include <shlobj.h> | 10 #include <shlobj.h> |
| (...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 197 static_cast<BrowserDistribution::Type>(i); | 197 static_cast<BrowserDistribution::Type>(i); |
| 198 | 198 |
| 199 if (!installer_state->FindProduct(type)) { | 199 if (!installer_state->FindProduct(type)) { |
| 200 const ProductState* state = | 200 const ProductState* state = |
| 201 original_state.GetProductState(installer_state->system_install(), | 201 original_state.GetProductState(installer_state->system_install(), |
| 202 type); | 202 type); |
| 203 if ((state != NULL) && state->is_multi_install()) { | 203 if ((state != NULL) && state->is_multi_install()) { |
| 204 installer_state->AddProductFromState(type, *state); | 204 installer_state->AddProductFromState(type, *state); |
| 205 VLOG(1) << "Product already installed and must be included: " | 205 VLOG(1) << "Product already installed and must be included: " |
| 206 << BrowserDistribution::GetSpecificDistribution(type)-> | 206 << BrowserDistribution::GetSpecificDistribution(type)-> |
| 207 GetAppShortCutName(); | 207 GetDisplayName(); |
| 208 } | 208 } |
| 209 } | 209 } |
| 210 } | 210 } |
| 211 } | 211 } |
| 212 } | 212 } |
| 213 | 213 |
| 214 // This function is called when --rename-chrome-exe option is specified on | 214 // This function is called when --rename-chrome-exe option is specified on |
| 215 // setup.exe command line. This function assumes an in-use update has happened | 215 // setup.exe command line. This function assumes an in-use update has happened |
| 216 // for Chrome so there should be a file called new_chrome.exe on the file | 216 // for Chrome so there should be a file called new_chrome.exe on the file |
| 217 // system and a key called 'opv' in the registry. This function will move | 217 // system and a key called 'opv' in the registry. This function will move |
| (...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 331 original_state.GetProductState(is_system_install, dist->GetType()); | 331 original_state.GetProductState(is_system_install, dist->GetType()); |
| 332 // Is an earlier version of this product already installed? | 332 // Is an earlier version of this product already installed? |
| 333 if (product_state != NULL && | 333 if (product_state != NULL && |
| 334 product_state->version().CompareTo(new_version) < 0) { | 334 product_state->version().CompareTo(new_version) < 0) { |
| 335 bool is_overridden = false; | 335 bool is_overridden = false; |
| 336 GoogleUpdateSettings::UpdatePolicy app_policy = | 336 GoogleUpdateSettings::UpdatePolicy app_policy = |
| 337 GoogleUpdateSettings::GetAppUpdatePolicy(dist->GetAppGuid(), | 337 GoogleUpdateSettings::GetAppUpdatePolicy(dist->GetAppGuid(), |
| 338 &is_overridden); | 338 &is_overridden); |
| 339 if (is_overridden && app_policy != binaries_policy) { | 339 if (is_overridden && app_policy != binaries_policy) { |
| 340 LOG(ERROR) << "Found legacy Group Policy setting for " | 340 LOG(ERROR) << "Found legacy Group Policy setting for " |
| 341 << dist->GetAppShortCutName() << " (value: " << app_policy | 341 << dist->GetDisplayName() << " (value: " << app_policy |
| 342 << ") that does not match the setting for " | 342 << ") that does not match the setting for " |
| 343 << binaries_dist->GetAppShortCutName() | 343 << binaries_dist->GetDisplayName() |
| 344 << " (value: " << binaries_policy << ")."; | 344 << " (value: " << binaries_policy << ")."; |
| 345 settings_are_valid = false; | 345 settings_are_valid = false; |
| 346 } | 346 } |
| 347 } | 347 } |
| 348 } | 348 } |
| 349 | 349 |
| 350 if (!settings_are_valid) { | 350 if (!settings_are_valid) { |
| 351 // TODO(grt): add " See http://goo.gl/+++ for details." to the end of this | 351 // TODO(grt): add " See http://goo.gl/+++ for details." to the end of this |
| 352 // log message and to the IDS_INSTALL_INCONSISTENT_UPDATE_POLICY string once | 352 // log message and to the IDS_INSTALL_INCONSISTENT_UPDATE_POLICY string once |
| 353 // we have a help center article that explains why this error is being | 353 // we have a help center article that explains why this error is being |
| 354 // reported and how to resolve it. | 354 // reported and how to resolve it. |
| 355 LOG(ERROR) << "Cannot apply update on account of inconsistent " | 355 LOG(ERROR) << "Cannot apply update on account of inconsistent " |
| 356 "Google Update Group Policy settings. Use the Group Policy " | 356 "Google Update Group Policy settings. Use the Group Policy " |
| 357 "Editor to set the update policy override for the " | 357 "Editor to set the update policy override for the " |
| 358 << binaries_dist->GetAppShortCutName() | 358 << binaries_dist->GetDisplayName() |
| 359 << " application and try again."; | 359 << " application and try again."; |
| 360 *status = installer::INCONSISTENT_UPDATE_POLICY; | 360 *status = installer::INCONSISTENT_UPDATE_POLICY; |
| 361 installer_state.WriteInstallerResult( | 361 installer_state.WriteInstallerResult( |
| 362 *status, IDS_INSTALL_INCONSISTENT_UPDATE_POLICY_BASE, NULL); | 362 *status, IDS_INSTALL_INCONSISTENT_UPDATE_POLICY_BASE, NULL); |
| 363 } | 363 } |
| 364 | 364 |
| 365 return settings_are_valid; | 365 return settings_are_valid; |
| 366 #endif // defined(GOOGLE_CHROME_BUILD) | 366 #endif // defined(GOOGLE_CHROME_BUILD) |
| 367 } | 367 } |
| 368 | 368 |
| (...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 498 } else { | 498 } else { |
| 499 // This is a non-multi installation. | 499 // This is a non-multi installation. |
| 500 | 500 |
| 501 // Check for an existing installation of the product. | 501 // Check for an existing installation of the product. |
| 502 const ProductState* product_state = original_state.GetProductState( | 502 const ProductState* product_state = original_state.GetProductState( |
| 503 system_level, products[0]->distribution()->GetType()); | 503 system_level, products[0]->distribution()->GetType()); |
| 504 if (product_state != NULL) { | 504 if (product_state != NULL) { |
| 505 // Block downgrades from multi-install to single-install. | 505 // Block downgrades from multi-install to single-install. |
| 506 if (product_state->is_multi_install()) { | 506 if (product_state->is_multi_install()) { |
| 507 LOG(ERROR) << "Multi-install " | 507 LOG(ERROR) << "Multi-install " |
| 508 << products[0]->distribution()->GetAppShortCutName() | 508 << products[0]->distribution()->GetDisplayName() |
| 509 << " exists; aborting single install."; | 509 << " exists; aborting single install."; |
| 510 *status = installer::MULTI_INSTALLATION_EXISTS; | 510 *status = installer::MULTI_INSTALLATION_EXISTS; |
| 511 installer_state->WriteInstallerResult(*status, | 511 installer_state->WriteInstallerResult(*status, |
| 512 IDS_INSTALL_MULTI_INSTALLATION_EXISTS_BASE, NULL); | 512 IDS_INSTALL_MULTI_INSTALLATION_EXISTS_BASE, NULL); |
| 513 return false; | 513 return false; |
| 514 } | 514 } |
| 515 } | 515 } |
| 516 } | 516 } |
| 517 | 517 |
| 518 return true; | 518 return true; |
| (...skipping 231 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 750 bool remove_all, | 750 bool remove_all, |
| 751 bool force_uninstall, | 751 bool force_uninstall, |
| 752 const Product& product) { | 752 const Product& product) { |
| 753 const ProductState* product_state = | 753 const ProductState* product_state = |
| 754 original_state.GetProductState(installer_state.system_install(), | 754 original_state.GetProductState(installer_state.system_install(), |
| 755 product.distribution()->GetType()); | 755 product.distribution()->GetType()); |
| 756 if (product_state != NULL) { | 756 if (product_state != NULL) { |
| 757 VLOG(1) << "version on the system: " | 757 VLOG(1) << "version on the system: " |
| 758 << product_state->version().GetString(); | 758 << product_state->version().GetString(); |
| 759 } else if (!force_uninstall) { | 759 } else if (!force_uninstall) { |
| 760 LOG(ERROR) << product.distribution()->GetAppShortCutName() | 760 LOG(ERROR) << product.distribution()->GetDisplayName() |
| 761 << " not found for uninstall."; | 761 << " not found for uninstall."; |
| 762 return installer::CHROME_NOT_INSTALLED; | 762 return installer::CHROME_NOT_INSTALLED; |
| 763 } | 763 } |
| 764 | 764 |
| 765 return installer::UninstallProduct( | 765 return installer::UninstallProduct( |
| 766 original_state, installer_state, cmd_line.GetProgram(), product, | 766 original_state, installer_state, cmd_line.GetProgram(), product, |
| 767 remove_all, force_uninstall, cmd_line); | 767 remove_all, force_uninstall, cmd_line); |
| 768 } | 768 } |
| 769 | 769 |
| 770 installer::InstallStatus UninstallProducts( | 770 installer::InstallStatus UninstallProducts( |
| (...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 922 original_state.GetProductState(false, | 922 original_state.GetProductState(false, |
| 923 BrowserDistribution::CHROME_BROWSER); | 923 BrowserDistribution::CHROME_BROWSER); |
| 924 if (!existing_chrome) { | 924 if (!existing_chrome) { |
| 925 existing_chrome = | 925 existing_chrome = |
| 926 original_state.GetProductState(true, BrowserDistribution::CHROME_BROWSER); | 926 original_state.GetProductState(true, BrowserDistribution::CHROME_BROWSER); |
| 927 } | 927 } |
| 928 if (existing_chrome) { | 928 if (existing_chrome) { |
| 929 static const wchar_t kPleaseUninstallYourChromeMessage[] = | 929 static const wchar_t kPleaseUninstallYourChromeMessage[] = |
| 930 L"You already have a full-installation (non-dev) of %1ls, please " | 930 L"You already have a full-installation (non-dev) of %1ls, please " |
| 931 L"uninstall it first using Add/Remove Programs in the control panel."; | 931 L"uninstall it first using Add/Remove Programs in the control panel."; |
| 932 string16 name(chrome_dist->GetAppShortCutName()); | 932 string16 name(chrome_dist->GetDisplayName()); |
| 933 string16 message(base::StringPrintf(kPleaseUninstallYourChromeMessage, | 933 string16 message(base::StringPrintf(kPleaseUninstallYourChromeMessage, |
| 934 name.c_str())); | 934 name.c_str())); |
| 935 | 935 |
| 936 LOG(ERROR) << "Aborting operation: another installation of " << name | 936 LOG(ERROR) << "Aborting operation: another installation of " << name |
| 937 << " was found, as a last resort (if the product is not present " | 937 << " was found, as a last resort (if the product is not present " |
| 938 "in Add/Remove Programs), try executing: " | 938 "in Add/Remove Programs), try executing: " |
| 939 << existing_chrome->uninstall_command().GetCommandLineString(); | 939 << existing_chrome->uninstall_command().GetCommandLineString(); |
| 940 MessageBox(NULL, message.c_str(), NULL, MB_ICONERROR); | 940 MessageBox(NULL, message.c_str(), NULL, MB_ICONERROR); |
| 941 return installer::INSTALL_FAILED; | 941 return installer::INSTALL_FAILED; |
| 942 } | 942 } |
| (...skipping 291 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1234 for (Products::const_iterator it = products.begin(); it < products.end(); | 1234 for (Products::const_iterator it = products.begin(); it < products.end(); |
| 1235 ++it) { | 1235 ++it) { |
| 1236 const Product& product = **it; | 1236 const Product& product = **it; |
| 1237 BrowserDistribution* browser_dist = product.distribution(); | 1237 BrowserDistribution* browser_dist = product.distribution(); |
| 1238 // We started as system-level and have been re-launched as user level | 1238 // We started as system-level and have been re-launched as user level |
| 1239 // to continue with the toast experiment. | 1239 // to continue with the toast experiment. |
| 1240 Version installed_version; | 1240 Version installed_version; |
| 1241 InstallUtil::GetChromeVersion(browser_dist, true, &installed_version); | 1241 InstallUtil::GetChromeVersion(browser_dist, true, &installed_version); |
| 1242 if (!installed_version.IsValid()) { | 1242 if (!installed_version.IsValid()) { |
| 1243 LOG(ERROR) << "No installation of " | 1243 LOG(ERROR) << "No installation of " |
| 1244 << browser_dist->GetAppShortCutName() | 1244 << browser_dist->GetDisplayName() |
| 1245 << " found for system-level toast."; | 1245 << " found for system-level toast."; |
| 1246 } else { | 1246 } else { |
| 1247 product.LaunchUserExperiment( | 1247 product.LaunchUserExperiment( |
| 1248 cmd_line.GetProgram(), installer::REENTRY_SYS_UPDATE, true); | 1248 cmd_line.GetProgram(), installer::REENTRY_SYS_UPDATE, true); |
| 1249 } | 1249 } |
| 1250 } | 1250 } |
| 1251 } else if (cmd_line.HasSwitch( | 1251 } else if (cmd_line.HasSwitch( |
| 1252 installer::switches::kChromeFrameReadyModeOptIn)) { | 1252 installer::switches::kChromeFrameReadyModeOptIn)) { |
| 1253 *exit_code = InstallUtil::GetInstallReturnCode( | 1253 *exit_code = InstallUtil::GetInstallReturnCode( |
| 1254 installer::ChromeFrameReadyModeOptIn(original_state, *installer_state)); | 1254 installer::ChromeFrameReadyModeOptIn(original_state, *installer_state)); |
| (...skipping 269 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1524 const Products& products = installer_state.products(); | 1524 const Products& products = installer_state.products(); |
| 1525 for (Products::const_iterator it = products.begin(); it < products.end(); | 1525 for (Products::const_iterator it = products.begin(); it < products.end(); |
| 1526 ++it) { | 1526 ++it) { |
| 1527 const Product& product = **it; | 1527 const Product& product = **it; |
| 1528 const ProductState* product_state = | 1528 const ProductState* product_state = |
| 1529 original_state.GetProductState(system_install, | 1529 original_state.GetProductState(system_install, |
| 1530 product.distribution()->GetType()); | 1530 product.distribution()->GetType()); |
| 1531 if (product_state != NULL && | 1531 if (product_state != NULL && |
| 1532 (product_state->version().CompareTo(*installer_version) > 0)) { | 1532 (product_state->version().CompareTo(*installer_version) > 0)) { |
| 1533 LOG(ERROR) << "Higher version of " | 1533 LOG(ERROR) << "Higher version of " |
| 1534 << product.distribution()->GetAppShortCutName() | 1534 << product.distribution()->GetDisplayName() |
| 1535 << " is already installed."; | 1535 << " is already installed."; |
| 1536 higher_products |= (1 << product.distribution()->GetType()); | 1536 higher_products |= (1 << product.distribution()->GetType()); |
| 1537 } | 1537 } |
| 1538 } | 1538 } |
| 1539 | 1539 |
| 1540 if (higher_products != 0) { | 1540 if (higher_products != 0) { |
| 1541 COMPILE_ASSERT(BrowserDistribution::NUM_TYPES == 4, | 1541 COMPILE_ASSERT(BrowserDistribution::NUM_TYPES == 4, |
| 1542 add_support_for_new_products_here_); | 1542 add_support_for_new_products_here_); |
| 1543 const uint32 kBrowserBit = 1 << BrowserDistribution::CHROME_BROWSER; | 1543 const uint32 kBrowserBit = 1 << BrowserDistribution::CHROME_BROWSER; |
| 1544 const uint32 kGCFBit = 1 << BrowserDistribution::CHROME_FRAME; | 1544 const uint32 kGCFBit = 1 << BrowserDistribution::CHROME_FRAME; |
| (...skipping 287 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1832 int num_products = 0; | 1832 int num_products = 0; |
| 1833 for (Products::const_iterator it = products.begin(); it < products.end(); | 1833 for (Products::const_iterator it = products.begin(); it < products.end(); |
| 1834 ++it) { | 1834 ++it) { |
| 1835 if (!(*it)->is_chrome_binaries()) | 1835 if (!(*it)->is_chrome_binaries()) |
| 1836 ++num_products; | 1836 ++num_products; |
| 1837 } | 1837 } |
| 1838 if (num_products == 1U) { | 1838 if (num_products == 1U) { |
| 1839 ::MessageBoxW(NULL, | 1839 ::MessageBoxW(NULL, |
| 1840 installer::GetLocalizedString( | 1840 installer::GetLocalizedString( |
| 1841 IDS_UNINSTALL_COMPLETE_BASE).c_str(), | 1841 IDS_UNINSTALL_COMPLETE_BASE).c_str(), |
| 1842 cf_install->distribution()->GetAppShortCutName().c_str(), | 1842 cf_install->distribution()->GetDisplayName().c_str(), |
| 1843 MB_OK); | 1843 MB_OK); |
| 1844 } | 1844 } |
| 1845 } | 1845 } |
| 1846 } | 1846 } |
| 1847 | 1847 |
| 1848 int return_code = 0; | 1848 int return_code = 0; |
| 1849 // MSI demands that custom actions always return 0 (ERROR_SUCCESS) or it will | 1849 // MSI demands that custom actions always return 0 (ERROR_SUCCESS) or it will |
| 1850 // rollback the action. If we're uninstalling we want to avoid this, so always | 1850 // rollback the action. If we're uninstalling we want to avoid this, so always |
| 1851 // report success, squashing any more informative return codes. | 1851 // report success, squashing any more informative return codes. |
| 1852 if (!(installer_state.is_msi() && is_uninstall)) | 1852 if (!(installer_state.is_msi() && is_uninstall)) |
| 1853 // Note that we allow the status installer::UNINSTALL_REQUIRES_REBOOT | 1853 // Note that we allow the status installer::UNINSTALL_REQUIRES_REBOOT |
| 1854 // to pass through, since this is only returned on uninstall which is | 1854 // to pass through, since this is only returned on uninstall which is |
| 1855 // never invoked directly by Google Update. | 1855 // never invoked directly by Google Update. |
| 1856 return_code = InstallUtil::GetInstallReturnCode(install_status); | 1856 return_code = InstallUtil::GetInstallReturnCode(install_status); |
| 1857 | 1857 |
| 1858 VLOG(1) << "Installation complete, returning: " << return_code; | 1858 VLOG(1) << "Installation complete, returning: " << return_code; |
| 1859 | 1859 |
| 1860 return return_code; | 1860 return return_code; |
| 1861 } | 1861 } |
| OLD | NEW |