| OLD | NEW |
| 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2006-2008 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 <windows.h> | 5 #include <windows.h> |
| 6 #include <shlobj.h> | 6 #include <shlobj.h> |
| 7 | 7 |
| 8 #include <sstream> | 8 #include <sstream> |
| 9 | 9 |
| 10 #include "chrome/browser/first_run.h" | 10 #include "chrome/browser/first_run.h" |
| (...skipping 188 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 199 exe = L"Global\\" + exe; | 199 exe = L"Global\\" + exe; |
| 200 if (handle != NULL) | 200 if (handle != NULL) |
| 201 CloseHandle(handle); | 201 CloseHandle(handle); |
| 202 handle = CreateEvent(NULL, TRUE, TRUE, exe.c_str()); | 202 handle = CreateEvent(NULL, TRUE, TRUE, exe.c_str()); |
| 203 int error = GetLastError(); | 203 int error = GetLastError(); |
| 204 return (error == ERROR_ALREADY_EXISTS || error == ERROR_ACCESS_DENIED); | 204 return (error == ERROR_ALREADY_EXISTS || error == ERROR_ACCESS_DENIED); |
| 205 } | 205 } |
| 206 | 206 |
| 207 bool Upgrade::RelaunchChromeBrowser(const CommandLine& command_line) { | 207 bool Upgrade::RelaunchChromeBrowser(const CommandLine& command_line) { |
| 208 ::SetEnvironmentVariable(google_update::kEnvProductVersionKey, NULL); | 208 ::SetEnvironmentVariable(google_update::kEnvProductVersionKey, NULL); |
| 209 return process_util::LaunchApp(command_line.command_line_string(), | 209 return base::LaunchApp(command_line.command_line_string(), |
| 210 false, false, NULL); | 210 false, false, NULL); |
| 211 } | 211 } |
| 212 | 212 |
| 213 bool Upgrade::SwapNewChromeExeIfPresent() { | 213 bool Upgrade::SwapNewChromeExeIfPresent() { |
| 214 std::wstring new_chrome_exe; | 214 std::wstring new_chrome_exe; |
| 215 if (!GetNewerChromeFile(&new_chrome_exe)) | 215 if (!GetNewerChromeFile(&new_chrome_exe)) |
| 216 return false; | 216 return false; |
| 217 if (!file_util::PathExists(new_chrome_exe)) | 217 if (!file_util::PathExists(new_chrome_exe)) |
| 218 return false; | 218 return false; |
| 219 std::wstring old_chrome_exe; | 219 std::wstring old_chrome_exe; |
| 220 if (!PathService::Get(base::FILE_EXE, &old_chrome_exe)) | 220 if (!PathService::Get(base::FILE_EXE, &old_chrome_exe)) |
| 221 return false; | 221 return false; |
| 222 RegKey key; | 222 RegKey key; |
| 223 HKEY reg_root = InstallUtil::IsPerUserInstall(old_chrome_exe.c_str()) ? | 223 HKEY reg_root = InstallUtil::IsPerUserInstall(old_chrome_exe.c_str()) ? |
| 224 HKEY_CURRENT_USER : HKEY_LOCAL_MACHINE; | 224 HKEY_CURRENT_USER : HKEY_LOCAL_MACHINE; |
| 225 BrowserDistribution *dist = BrowserDistribution::GetDistribution(); | 225 BrowserDistribution *dist = BrowserDistribution::GetDistribution(); |
| 226 std::wstring rename_cmd; | 226 std::wstring rename_cmd; |
| 227 if (key.Open(reg_root, dist->GetVersionKey().c_str(), KEY_READ) && | 227 if (key.Open(reg_root, dist->GetVersionKey().c_str(), KEY_READ) && |
| 228 key.ReadValue(google_update::kRegRenameCmdField, &rename_cmd)) { | 228 key.ReadValue(google_update::kRegRenameCmdField, &rename_cmd)) { |
| 229 ProcessHandle handle; | 229 base::ProcessHandle handle; |
| 230 if (process_util::LaunchApp(rename_cmd, true, true, &handle)) { | 230 if (base::LaunchApp(rename_cmd, true, true, &handle)) { |
| 231 DWORD exit_code; | 231 DWORD exit_code; |
| 232 ::GetExitCodeProcess(handle, &exit_code); | 232 ::GetExitCodeProcess(handle, &exit_code); |
| 233 ::CloseHandle(handle); | 233 ::CloseHandle(handle); |
| 234 if (exit_code == installer_util::RENAME_SUCCESSFUL) | 234 if (exit_code == installer_util::RENAME_SUCCESSFUL) |
| 235 return true; | 235 return true; |
| 236 } | 236 } |
| 237 } | 237 } |
| 238 std::wstring backup_exe; | 238 std::wstring backup_exe; |
| 239 if (!GetBackupChromeFile(&backup_exe)) | 239 if (!GetBackupChromeFile(&backup_exe)) |
| 240 return false; | 240 return false; |
| (...skipping 19 matching lines...) Expand all Loading... |
| 260 | 260 |
| 261 // This class is used by FirstRun::ImportSettings to determine when the import | 261 // This class is used by FirstRun::ImportSettings to determine when the import |
| 262 // process has ended and what was the result of the operation as reported by | 262 // process has ended and what was the result of the operation as reported by |
| 263 // the process exit code. This class executes in the context of the main chrome | 263 // the process exit code. This class executes in the context of the main chrome |
| 264 // process. | 264 // process. |
| 265 class ImportProcessRunner : public base::ObjectWatcher::Delegate { | 265 class ImportProcessRunner : public base::ObjectWatcher::Delegate { |
| 266 public: | 266 public: |
| 267 // The constructor takes the importer process to watch and then it does a | 267 // The constructor takes the importer process to watch and then it does a |
| 268 // message loop blocking wait until the process ends. This object now owns | 268 // message loop blocking wait until the process ends. This object now owns |
| 269 // the import_process handle. | 269 // the import_process handle. |
| 270 explicit ImportProcessRunner(ProcessHandle import_process) | 270 explicit ImportProcessRunner(base::ProcessHandle import_process) |
| 271 : import_process_(import_process), | 271 : import_process_(import_process), |
| 272 exit_code_(ResultCodes::NORMAL_EXIT) { | 272 exit_code_(ResultCodes::NORMAL_EXIT) { |
| 273 watcher_.StartWatching(import_process, this); | 273 watcher_.StartWatching(import_process, this); |
| 274 MessageLoop::current()->Run(); | 274 MessageLoop::current()->Run(); |
| 275 } | 275 } |
| 276 virtual ~ImportProcessRunner() { | 276 virtual ~ImportProcessRunner() { |
| 277 ::CloseHandle(import_process_); | 277 ::CloseHandle(import_process_); |
| 278 } | 278 } |
| 279 // Returns the child process exit code. There are 3 expected values: | 279 // Returns the child process exit code. There are 3 expected values: |
| 280 // NORMAL_EXIT, IMPORTER_CANCEL or IMPORTER_HUNG. | 280 // NORMAL_EXIT, IMPORTER_CANCEL or IMPORTER_HUNG. |
| 281 int exit_code() const { | 281 int exit_code() const { |
| 282 return exit_code_; | 282 return exit_code_; |
| 283 } | 283 } |
| 284 // The child process has terminated. Find the exit code and quit the loop. | 284 // The child process has terminated. Find the exit code and quit the loop. |
| 285 virtual void OnObjectSignaled(HANDLE object) { | 285 virtual void OnObjectSignaled(HANDLE object) { |
| 286 DCHECK(object == import_process_); | 286 DCHECK(object == import_process_); |
| 287 if (!::GetExitCodeProcess(import_process_, &exit_code_)) { | 287 if (!::GetExitCodeProcess(import_process_, &exit_code_)) { |
| 288 NOTREACHED(); | 288 NOTREACHED(); |
| 289 } | 289 } |
| 290 MessageLoop::current()->Quit(); | 290 MessageLoop::current()->Quit(); |
| 291 } | 291 } |
| 292 | 292 |
| 293 private: | 293 private: |
| 294 base::ObjectWatcher watcher_; | 294 base::ObjectWatcher watcher_; |
| 295 ProcessHandle import_process_; | 295 base::ProcessHandle import_process_; |
| 296 DWORD exit_code_; | 296 DWORD exit_code_; |
| 297 }; | 297 }; |
| 298 | 298 |
| 299 // Check every 3 seconds if the importer UI has hung. | 299 // Check every 3 seconds if the importer UI has hung. |
| 300 const int kPollHangFrequency = 3000; | 300 const int kPollHangFrequency = 3000; |
| 301 | 301 |
| 302 // This class specializes on finding hung 'owned' windows. Unfortunately, the | 302 // This class specializes on finding hung 'owned' windows. Unfortunately, the |
| 303 // HungWindowDetector class cannot be used here because it assumes child | 303 // HungWindowDetector class cannot be used here because it assumes child |
| 304 // windows and not owned top-level windows. | 304 // windows and not owned top-level windows. |
| 305 // This code is executed in the context of the main browser process and will | 305 // This code is executed in the context of the main browser process and will |
| 306 // terminate the importer process if it is hung. | 306 // terminate the importer process if it is hung. |
| 307 class HungImporterMonitor : public WorkerThreadTicker::Callback { | 307 class HungImporterMonitor : public WorkerThreadTicker::Callback { |
| 308 public: | 308 public: |
| 309 // The ctor takes the owner popup window and the process handle of the | 309 // The ctor takes the owner popup window and the process handle of the |
| 310 // process to kill in case the popup or its owned active popup become | 310 // process to kill in case the popup or its owned active popup become |
| 311 // unresponsive. | 311 // unresponsive. |
| 312 HungImporterMonitor(HWND owner_window, ProcessHandle import_process) | 312 HungImporterMonitor(HWND owner_window, base::ProcessHandle import_process) |
| 313 : owner_window_(owner_window), | 313 : owner_window_(owner_window), |
| 314 import_process_(import_process), | 314 import_process_(import_process), |
| 315 ticker_(kPollHangFrequency) { | 315 ticker_(kPollHangFrequency) { |
| 316 ticker_.RegisterTickHandler(this); | 316 ticker_.RegisterTickHandler(this); |
| 317 ticker_.Start(); | 317 ticker_.Start(); |
| 318 } | 318 } |
| 319 virtual ~HungImporterMonitor() { | 319 virtual ~HungImporterMonitor() { |
| 320 ticker_.Stop(); | 320 ticker_.Stop(); |
| 321 ticker_.UnregisterTickHandler(this); | 321 ticker_.UnregisterTickHandler(this); |
| 322 } | 322 } |
| 323 | 323 |
| 324 private: | 324 private: |
| 325 virtual void OnTick() { | 325 virtual void OnTick() { |
| 326 if (!import_process_) | 326 if (!import_process_) |
| 327 return; | 327 return; |
| 328 // We find the top active popup that we own, this will be either the | 328 // We find the top active popup that we own, this will be either the |
| 329 // owner_window_ itself or the dialog window of the other process. In | 329 // owner_window_ itself or the dialog window of the other process. In |
| 330 // both cases it is worth hung testing because both windows share the | 330 // both cases it is worth hung testing because both windows share the |
| 331 // same message queue and at some point the other window could be gone | 331 // same message queue and at some point the other window could be gone |
| 332 // while the other process still not pumping messages. | 332 // while the other process still not pumping messages. |
| 333 HWND active_window = ::GetLastActivePopup(owner_window_); | 333 HWND active_window = ::GetLastActivePopup(owner_window_); |
| 334 if (::IsHungAppWindow(active_window) || ::IsHungAppWindow(owner_window_)) { | 334 if (::IsHungAppWindow(active_window) || ::IsHungAppWindow(owner_window_)) { |
| 335 ::TerminateProcess(import_process_, ResultCodes::IMPORTER_HUNG); | 335 ::TerminateProcess(import_process_, ResultCodes::IMPORTER_HUNG); |
| 336 import_process_ = NULL; | 336 import_process_ = NULL; |
| 337 } | 337 } |
| 338 } | 338 } |
| 339 | 339 |
| 340 HWND owner_window_; | 340 HWND owner_window_; |
| 341 ProcessHandle import_process_; | 341 base::ProcessHandle import_process_; |
| 342 WorkerThreadTicker ticker_; | 342 WorkerThreadTicker ticker_; |
| 343 DISALLOW_EVIL_CONSTRUCTORS(HungImporterMonitor); | 343 DISALLOW_EVIL_CONSTRUCTORS(HungImporterMonitor); |
| 344 }; | 344 }; |
| 345 | 345 |
| 346 // This class is used by FirstRun::ImportNow to get notified of the outcome of | 346 // This class is used by FirstRun::ImportNow to get notified of the outcome of |
| 347 // the import operation. It differs from ImportProcessRunner in that this | 347 // the import operation. It differs from ImportProcessRunner in that this |
| 348 // class executes in the context of importing child process. | 348 // class executes in the context of importing child process. |
| 349 // The values that it handles are meant to be used as the process exit code. | 349 // The values that it handles are meant to be used as the process exit code. |
| 350 class FirstRunImportObserver : public ImportObserver { | 350 class FirstRunImportObserver : public ImportObserver { |
| 351 public: | 351 public: |
| (...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 411 if (cmdline.HasSwitch(switch_names[i])) { | 411 if (cmdline.HasSwitch(switch_names[i])) { |
| 412 CommandLine::AppendSwitchWithValue( | 412 CommandLine::AppendSwitchWithValue( |
| 413 &import_cmd, switch_names[i], | 413 &import_cmd, switch_names[i], |
| 414 cmdline.GetSwitchValue(switch_names[i])); | 414 cmdline.GetSwitchValue(switch_names[i])); |
| 415 } | 415 } |
| 416 } | 416 } |
| 417 CommandLine::AppendSwitchWithValue(&import_cmd, switches::kImport, | 417 CommandLine::AppendSwitchWithValue(&import_cmd, switches::kImport, |
| 418 EncodeImportParams(browser, items_to_import, parent_window)); | 418 EncodeImportParams(browser, items_to_import, parent_window)); |
| 419 | 419 |
| 420 // Time to launch the process that is going to do the import. | 420 // Time to launch the process that is going to do the import. |
| 421 ProcessHandle import_process; | 421 base::ProcessHandle import_process; |
| 422 if (!process_util::LaunchApp(import_cmd, false, false, &import_process)) | 422 if (!base::LaunchApp(import_cmd, false, false, &import_process)) |
| 423 return false; | 423 return false; |
| 424 | 424 |
| 425 // Activate the importer monitor. It awakes periodically in another thread | 425 // Activate the importer monitor. It awakes periodically in another thread |
| 426 // and checks that the importer UI is still pumping messages. | 426 // and checks that the importer UI is still pumping messages. |
| 427 if (parent_window) | 427 if (parent_window) |
| 428 HungImporterMonitor hang_monitor(parent_window, import_process); | 428 HungImporterMonitor hang_monitor(parent_window, import_process); |
| 429 | 429 |
| 430 // We block inside the import_runner ctor, pumping messages until the | 430 // We block inside the import_runner ctor, pumping messages until the |
| 431 // importer process ends. This can happen either by completing the import | 431 // importer process ends. This can happen either by completing the import |
| 432 // or by hang_monitor killing it. | 432 // or by hang_monitor killing it. |
| (...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 489 bool FirstRun::SetShowWelcomePagePref() { | 489 bool FirstRun::SetShowWelcomePagePref() { |
| 490 PrefService* local_state = g_browser_process->local_state(); | 490 PrefService* local_state = g_browser_process->local_state(); |
| 491 if (!local_state) | 491 if (!local_state) |
| 492 return false; | 492 return false; |
| 493 if (!local_state->IsPrefRegistered(prefs::kShouldShowWelcomePage)) { | 493 if (!local_state->IsPrefRegistered(prefs::kShouldShowWelcomePage)) { |
| 494 local_state->RegisterBooleanPref(prefs::kShouldShowWelcomePage, false); | 494 local_state->RegisterBooleanPref(prefs::kShouldShowWelcomePage, false); |
| 495 local_state->SetBoolean(prefs::kShouldShowWelcomePage, true); | 495 local_state->SetBoolean(prefs::kShouldShowWelcomePage, true); |
| 496 } | 496 } |
| 497 return true; | 497 return true; |
| 498 } | 498 } |
| OLD | NEW |