| OLD | NEW |
| 1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 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/gcapi/gcapi.h" | 5 #include "chrome/installer/gcapi/gcapi.h" |
| 6 | 6 |
| 7 #include <atlbase.h> | 7 #include <atlbase.h> |
| 8 #include <atlcom.h> | 8 #include <atlcom.h> |
| 9 #include <windows.h> | 9 #include <windows.h> |
| 10 #include <sddl.h> | 10 #include <sddl.h> |
| 11 #include <stdlib.h> | 11 #define STRSAFE_NO_DEPRECATE |
| 12 #include <strsafe.h> | 12 #include <strsafe.h> |
| 13 #include <tlhelp32.h> | 13 #include <tlhelp32.h> |
| 14 | 14 |
| 15 #include <cstdlib> |
| 16 |
| 15 #include "google_update_idl.h" | 17 #include "google_update_idl.h" |
| 16 | 18 |
| 17 namespace { | 19 namespace { |
| 18 | 20 |
| 19 const wchar_t kChromeRegClientsKey[] = | 21 const wchar_t kChromeRegClientsKey[] = |
| 20 L"Software\\Google\\Update\\Clients\\" | 22 L"Software\\Google\\Update\\Clients\\" |
| 21 L"{8A69D345-D564-463c-AFF1-A69D9E530F96}"; | 23 L"{8A69D345-D564-463c-AFF1-A69D9E530F96}"; |
| 22 const wchar_t kChromeRegClientStateKey[] = | 24 const wchar_t kChromeRegClientStateKey[] = |
| 23 L"Software\\Google\\Update\\ClientState\\" | 25 L"Software\\Google\\Update\\ClientState\\" |
| 24 L"{8A69D345-D564-463c-AFF1-A69D9E530F96}"; | 26 L"{8A69D345-D564-463c-AFF1-A69D9E530F96}"; |
| (...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 149 reinterpret_cast<LPDWORD>(size)) == ERROR_SUCCESS)) { | 151 reinterpret_cast<LPDWORD>(size)) == ERROR_SUCCESS)) { |
| 150 ::RegCloseKey(key); | 152 ::RegCloseKey(key); |
| 151 return true; | 153 return true; |
| 152 } | 154 } |
| 153 return false; | 155 return false; |
| 154 } | 156 } |
| 155 | 157 |
| 156 bool IsChromeInstalled(HKEY root_key) { | 158 bool IsChromeInstalled(HKEY root_key) { |
| 157 wchar_t version[64]; | 159 wchar_t version[64]; |
| 158 size_t size = _countof(version); | 160 size_t size = _countof(version); |
| 159 if (ReadValueFromRegistry(root_key, kChromeRegClientsKey, kChromeRegVersion, | 161 return ReadValueFromRegistry(root_key, kChromeRegClientsKey, |
| 160 version, &size)) | 162 kChromeRegVersion, version, &size); |
| 161 return true; | |
| 162 return false; | |
| 163 } | 163 } |
| 164 | 164 |
| 165 bool IsWinXPSp2OrLater(bool* is_vista_or_later) { | 165 enum WindowsVersion { |
| 166 OSVERSIONINFOEX osviex = { sizeof(OSVERSIONINFOEX) }; | 166 VERSION_BELOW_XP_SP2, |
| 167 int r = ::GetVersionEx((LPOSVERSIONINFO)&osviex); | 167 VERSION_XP_SP2_UP_TO_VISTA, // "but not including" |
| 168 // If this failed we're on Win9X or a pre NT4SP6 OS. | 168 VERSION_VISTA_OR_HIGHER, |
| 169 if (!r) | 169 }; |
| 170 return false; | 170 WindowsVersion GetWindowsVersion() { |
| 171 OSVERSIONINFOEX version_info = { sizeof version_info }; |
| 172 GetVersionEx(reinterpret_cast<OSVERSIONINFO*>(&version_info)); |
| 171 | 173 |
| 172 if (osviex.dwMajorVersion < 5) | 174 // Windows Vista is version 6.0. |
| 173 return false; | 175 if (version_info.dwMajorVersion >= 6) |
| 176 return VERSION_VISTA_OR_HIGHER; |
| 174 | 177 |
| 175 if (osviex.dwMajorVersion > 5) { | 178 // Windows XP is version 5.1. (5.2 is Windows Server 2003/XP Pro x64.) |
| 176 *is_vista_or_later = true; | 179 if ((version_info.dwMajorVersion < 5) || (version_info.dwMinorVersion < 1)) |
| 177 return true; // way beyond Windows XP; | 180 return VERSION_BELOW_XP_SP2; |
| 178 } | |
| 179 | 181 |
| 180 if (osviex.dwMinorVersion >= 1 && osviex.wServicePackMajor >= 2) | 182 // For XP itself, we only support SP2 and above. |
| 181 return true; // Windows XP SP2 or better. | 183 return ((version_info.dwMinorVersion > 1) || |
| 182 | 184 (version_info.wServicePackMajor >= 2)) ? |
| 183 return false; // Windows 2000, WinXP no Service Pack. | 185 VERSION_XP_SP2_UP_TO_VISTA : VERSION_BELOW_XP_SP2; |
| 184 } | 186 } |
| 185 | 187 |
| 186 // Note this function should not be called on old Windows versions where these | 188 // Note this function should not be called on old Windows versions where these |
| 187 // Windows API are not available. We always invoke this function after checking | 189 // Windows API are not available. We always invoke this function after checking |
| 188 // that current OS is Vista or later. | 190 // that current OS is Vista or later. |
| 189 bool VerifyAdminGroup() { | 191 bool VerifyAdminGroup() { |
| 190 SID_IDENTIFIER_AUTHORITY NtAuthority = SECURITY_NT_AUTHORITY; | 192 SID_IDENTIFIER_AUTHORITY NtAuthority = SECURITY_NT_AUTHORITY; |
| 191 PSID Group; | 193 PSID Group; |
| 192 BOOL check = ::AllocateAndInitializeSid(&NtAuthority, 2, | 194 BOOL check = ::AllocateAndInitializeSid(&NtAuthority, 2, |
| 193 SECURITY_BUILTIN_DOMAIN_RID, | 195 SECURITY_BUILTIN_DOMAIN_RID, |
| (...skipping 29 matching lines...) Expand all Loading... |
| 223 RegDeleteKey(key, NULL); | 225 RegDeleteKey(key, NULL); |
| 224 | 226 |
| 225 RegCloseKey(key); | 227 RegCloseKey(key); |
| 226 } | 228 } |
| 227 | 229 |
| 228 return result; | 230 return result; |
| 229 } | 231 } |
| 230 | 232 |
| 231 bool IsRunningElevated() { | 233 bool IsRunningElevated() { |
| 232 // This method should be called only for Vista or later. | 234 // This method should be called only for Vista or later. |
| 233 bool is_vista_or_later = false; | 235 if ((GetWindowsVersion() < VERSION_VISTA_OR_HIGHER) || |
| 234 IsWinXPSp2OrLater(&is_vista_or_later); | 236 !VerifyAdminGroup()) |
| 235 if (!is_vista_or_later || !VerifyAdminGroup()) | |
| 236 return false; | 237 return false; |
| 237 | 238 |
| 238 HANDLE process_token; | 239 HANDLE process_token; |
| 239 if (!::OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &process_token)) | 240 if (!::OpenProcessToken(GetCurrentProcess(), TOKEN_QUERY, &process_token)) |
| 240 return false; | 241 return false; |
| 241 | 242 |
| 242 TOKEN_ELEVATION_TYPE elevation_type = TokenElevationTypeDefault; | 243 TOKEN_ELEVATION_TYPE elevation_type = TokenElevationTypeDefault; |
| 243 DWORD size_returned = 0; | 244 DWORD size_returned = 0; |
| 244 if (!::GetTokenInformation(process_token, TokenElevationType, | 245 if (!::GetTokenInformation(process_token, TokenElevationType, |
| 245 &elevation_type, sizeof(elevation_type), | 246 &elevation_type, sizeof(elevation_type), |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 280 ::CloseHandle(process_handle); | 281 ::CloseHandle(process_handle); |
| 281 return result; | 282 return result; |
| 282 } | 283 } |
| 283 } // namespace | 284 } // namespace |
| 284 | 285 |
| 285 #pragma comment(linker, "/EXPORT:GoogleChromeCompatibilityCheck=_GoogleChromeCom
patibilityCheck@8,PRIVATE") | 286 #pragma comment(linker, "/EXPORT:GoogleChromeCompatibilityCheck=_GoogleChromeCom
patibilityCheck@8,PRIVATE") |
| 286 DLLEXPORT BOOL __stdcall GoogleChromeCompatibilityCheck(BOOL set_flag, | 287 DLLEXPORT BOOL __stdcall GoogleChromeCompatibilityCheck(BOOL set_flag, |
| 287 DWORD *reasons) { | 288 DWORD *reasons) { |
| 288 DWORD local_reasons = 0; | 289 DWORD local_reasons = 0; |
| 289 | 290 |
| 290 bool is_vista_or_later = false; | 291 WindowsVersion windows_version = GetWindowsVersion(); |
| 291 // System requirements? | 292 // System requirements? |
| 292 if (!IsWinXPSp2OrLater(&is_vista_or_later)) | 293 if (windows_version == VERSION_BELOW_XP_SP2) |
| 293 local_reasons |= GCCC_ERROR_OSNOTSUPPORTED; | 294 local_reasons |= GCCC_ERROR_OSNOTSUPPORTED; |
| 294 | 295 |
| 295 if (IsChromeInstalled(HKEY_LOCAL_MACHINE)) | 296 if (IsChromeInstalled(HKEY_LOCAL_MACHINE)) |
| 296 local_reasons |= GCCC_ERROR_SYSTEMLEVELALREADYPRESENT; | 297 local_reasons |= GCCC_ERROR_SYSTEMLEVELALREADYPRESENT; |
| 297 | 298 |
| 298 if (IsChromeInstalled(HKEY_CURRENT_USER)) | 299 if (IsChromeInstalled(HKEY_CURRENT_USER)) |
| 299 local_reasons |= GCCC_ERROR_USERLEVELALREADYPRESENT; | 300 local_reasons |= GCCC_ERROR_USERLEVELALREADYPRESENT; |
| 300 | 301 |
| 301 if (!VerifyHKLMAccess(kChromeRegClientsKey)) { | 302 if (!VerifyHKLMAccess(kChromeRegClientsKey)) { |
| 302 local_reasons |= GCCC_ERROR_ACCESSDENIED; | 303 local_reasons |= GCCC_ERROR_ACCESSDENIED; |
| 303 } else if (is_vista_or_later && !VerifyAdminGroup()) { | 304 } else if ((windows_version == VERSION_VISTA_OR_HIGHER) && |
| 305 !VerifyAdminGroup()) { |
| 304 // For Vista or later check for elevation since even for admin user we could | 306 // For Vista or later check for elevation since even for admin user we could |
| 305 // be running in non-elevated mode. We require integrity level High. | 307 // be running in non-elevated mode. We require integrity level High. |
| 306 local_reasons |= GCCC_ERROR_INTEGRITYLEVEL; | 308 local_reasons |= GCCC_ERROR_INTEGRITYLEVEL; |
| 307 } | 309 } |
| 308 | 310 |
| 309 // Then only check whether we can re-offer, if everything else is OK. | 311 // Then only check whether we can re-offer, if everything else is OK. |
| 310 if (local_reasons == 0 && !CanReOfferChrome(set_flag)) | 312 if (local_reasons == 0 && !CanReOfferChrome(set_flag)) |
| 311 local_reasons |= GCCC_ERROR_ALREADYOFFERED; | 313 local_reasons |= GCCC_ERROR_ALREADYOFFERED; |
| 312 | 314 |
| 313 // Done. Copy/return results. | 315 // Done. Copy/return results. |
| (...skipping 128 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 442 // This loop iterates through all of the top-level Windows named | 444 // This loop iterates through all of the top-level Windows named |
| 443 // Chrome_WindowImpl_0, and looks for the first one with any children. | 445 // Chrome_WindowImpl_0, and looks for the first one with any children. |
| 444 while (handle && !FindWindowEx(handle, NULL, L"Chrome_WindowImpl_0", NULL)) { | 446 while (handle && !FindWindowEx(handle, NULL, L"Chrome_WindowImpl_0", NULL)) { |
| 445 // Get the next top-level Chrome window. | 447 // Get the next top-level Chrome window. |
| 446 handle = FindWindowEx(NULL, handle, L"Chrome_WindowImpl_0", NULL); | 448 handle = FindWindowEx(NULL, handle, L"Chrome_WindowImpl_0", NULL); |
| 447 } | 449 } |
| 448 | 450 |
| 449 return (handle && | 451 return (handle && |
| 450 SetWindowPos(handle, 0, x, y, width, height, SWP_NOZORDER)); | 452 SetWindowPos(handle, 0, x, y, width, height, SWP_NOZORDER)); |
| 451 } | 453 } |
| OLD | NEW |