Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(120)

Side by Side Diff: chrome/browser/chrome_browser_main.cc

Issue 12674028: Report text output and exit code for command-line operations. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Forgotten review responses. Created 7 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « apps/apps.gypi ('k') | chrome/browser/chrome_process_singleton.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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/browser/chrome_browser_main.h" 5 #include "chrome/browser/chrome_browser_main.h"
6 6
7 #if defined(TOOLKIT_GTK) 7 #if defined(TOOLKIT_GTK)
8 #include <gtk/gtk.h> 8 #include <gtk/gtk.h>
9 #endif 9 #endif
10 10
11 #include <limits.h>
11 #include <string> 12 #include <string>
12 #include <vector> 13 #include <vector>
13 14
14 #include "base/at_exit.h" 15 #include "base/at_exit.h"
15 #include "base/bind.h" 16 #include "base/bind.h"
16 #include "base/command_line.h" 17 #include "base/command_line.h"
17 #include "base/debug/trace_event.h" 18 #include "base/debug/trace_event.h"
18 #include "base/file_util.h" 19 #include "base/file_util.h"
19 #include "base/files/file_path.h" 20 #include "base/files/file_path.h"
21 #include "base/memory/ref_counted.h"
20 #include "base/metrics/field_trial.h" 22 #include "base/metrics/field_trial.h"
21 #include "base/metrics/histogram.h" 23 #include "base/metrics/histogram.h"
22 #include "base/path_service.h" 24 #include "base/path_service.h"
23 #include "base/prefs/json_pref_store.h" 25 #include "base/prefs/json_pref_store.h"
24 #include "base/prefs/pref_registry_simple.h" 26 #include "base/prefs/pref_registry_simple.h"
25 #include "base/prefs/pref_service.h" 27 #include "base/prefs/pref_service.h"
26 #include "base/prefs/pref_value_store.h" 28 #include "base/prefs/pref_value_store.h"
27 #include "base/process_info.h" 29 #include "base/process_info.h"
28 #include "base/process_util.h" 30 #include "base/process_util.h"
29 #include "base/run_loop.h" 31 #include "base/run_loop.h"
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
64 #include "chrome/browser/metrics/metrics_log.h" 66 #include "chrome/browser/metrics/metrics_log.h"
65 #include "chrome/browser/metrics/metrics_service.h" 67 #include "chrome/browser/metrics/metrics_service.h"
66 #include "chrome/browser/metrics/thread_watcher.h" 68 #include "chrome/browser/metrics/thread_watcher.h"
67 #include "chrome/browser/metrics/tracking_synchronizer.h" 69 #include "chrome/browser/metrics/tracking_synchronizer.h"
68 #include "chrome/browser/metrics/variations/variations_service.h" 70 #include "chrome/browser/metrics/variations/variations_service.h"
69 #include "chrome/browser/nacl_host/nacl_process_host.h" 71 #include "chrome/browser/nacl_host/nacl_process_host.h"
70 #include "chrome/browser/net/chrome_net_log.h" 72 #include "chrome/browser/net/chrome_net_log.h"
71 #include "chrome/browser/net/crl_set_fetcher.h" 73 #include "chrome/browser/net/crl_set_fetcher.h"
72 #include "chrome/browser/notifications/desktop_notification_service.h" 74 #include "chrome/browser/notifications/desktop_notification_service.h"
73 #include "chrome/browser/notifications/desktop_notification_service_factory.h" 75 #include "chrome/browser/notifications/desktop_notification_service_factory.h"
76 #include "chrome/browser/operation_output.h"
74 #include "chrome/browser/page_cycler/page_cycler.h" 77 #include "chrome/browser/page_cycler/page_cycler.h"
75 #include "chrome/browser/performance_monitor/performance_monitor.h" 78 #include "chrome/browser/performance_monitor/performance_monitor.h"
76 #include "chrome/browser/performance_monitor/startup_timer.h" 79 #include "chrome/browser/performance_monitor/startup_timer.h"
77 #include "chrome/browser/plugins/plugin_prefs.h" 80 #include "chrome/browser/plugins/plugin_prefs.h"
78 #include "chrome/browser/policy/policy_service.h" 81 #include "chrome/browser/policy/policy_service.h"
79 #include "chrome/browser/prefs/chrome_pref_service_factory.h" 82 #include "chrome/browser/prefs/chrome_pref_service_factory.h"
80 #include "chrome/browser/prefs/command_line_pref_store.h" 83 #include "chrome/browser/prefs/command_line_pref_store.h"
81 #include "chrome/browser/prefs/scoped_user_pref_update.h" 84 #include "chrome/browser/prefs/scoped_user_pref_update.h"
82 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service.h" 85 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service.h"
83 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service_factory. h" 86 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service_factory. h"
(...skipping 324 matching lines...) Expand 10 before | Expand all | Expand 10 after
408 if (!command_line.HasSwitch(switches::kDisableCRLSets)) 411 if (!command_line.HasSwitch(switches::kDisableCRLSets))
409 g_browser_process->crl_set_fetcher()->StartInitialLoad(cus); 412 g_browser_process->crl_set_fetcher()->StartInitialLoad(cus);
410 #endif 413 #endif
411 414
412 g_browser_process->pnacl_component_installer()->RegisterPnaclComponent( 415 g_browser_process->pnacl_component_installer()->RegisterPnaclComponent(
413 cus, command_line); 416 cus, command_line);
414 417
415 cus->Start(); 418 cus->Start();
416 } 419 }
417 420
418 bool ProcessSingletonNotificationCallback( 421 bool ProcessSingletonOperationCallback(
419 const CommandLine& command_line, 422 const CommandLine& command_line,
420 const base::FilePath& current_directory) { 423 const base::FilePath& current_directory,
424 scoped_ptr<OperationOutput> operation_output) {
421 // Drop the request if the browser process is already in shutdown path. 425 // Drop the request if the browser process is already in shutdown path.
422 if (!g_browser_process || g_browser_process->IsShuttingDown()) 426 if (!g_browser_process || g_browser_process->IsShuttingDown())
423 return false; 427 return false;
424 428
425 g_browser_process->PlatformSpecificCommandLineProcessing(command_line); 429 g_browser_process->PlatformSpecificCommandLineProcessing(command_line);
426 430
427 // TODO(erikwright): Consider removing this - AFAIK it is no longer used. 431 // TODO(erikwright): Consider removing this - AFAIK it is no longer used.
428 // Handle the --uninstall-extension startup action. This needs to done here in 432 // Handle the --uninstall-extension startup action. This needs to done here in
429 // the process that is running with the target profile, otherwise the 433 // the process that is running with the target profile, otherwise the
430 // uninstall will fail to unload and remove all components. 434 // uninstall will fail to unload and remove all components.
(...skipping 13 matching lines...) Expand all
444 extension_startup_helper.UninstallExtension(command_line, profile); 448 extension_startup_helper.UninstallExtension(command_line, profile);
445 return true; 449 return true;
446 } 450 }
447 451
448 base::FilePath user_data_dir = 452 base::FilePath user_data_dir =
449 g_browser_process->profile_manager()->user_data_dir(); 453 g_browser_process->profile_manager()->user_data_dir();
450 base::FilePath startup_profile_dir = 454 base::FilePath startup_profile_dir =
451 GetStartupProfilePath(user_data_dir, command_line); 455 GetStartupProfilePath(user_data_dir, command_line);
452 456
453 StartupBrowserCreator::ProcessCommandLineAlreadyRunning( 457 StartupBrowserCreator::ProcessCommandLineAlreadyRunning(
454 command_line, current_directory, startup_profile_dir); 458 command_line,
459 current_directory,
460 startup_profile_dir,
461 operation_output.Pass());
455 return true; 462 return true;
456 } 463 }
457 464
458 void LaunchDevToolsHandlerIfNeeded(Profile* profile, 465 void LaunchDevToolsHandlerIfNeeded(Profile* profile,
459 const CommandLine& command_line) { 466 const CommandLine& command_line) {
460 if (command_line.HasSwitch(::switches::kRemoteDebuggingPort)) { 467 if (command_line.HasSwitch(::switches::kRemoteDebuggingPort)) {
461 std::string port_str = 468 std::string port_str =
462 command_line.GetSwitchValueASCII(::switches::kRemoteDebuggingPort); 469 command_line.GetSwitchValueASCII(::switches::kRemoteDebuggingPort);
463 int port; 470 int port;
464 if (base::StringToInt(port_str, &port) && port > 0 && port < 65535) { 471 if (base::StringToInt(port_str, &port) && port > 0 && port < 65535) {
(...skipping 277 matching lines...) Expand 10 before | Expand all | Expand 10 after
742 run_message_loop_ = false; 749 run_message_loop_ = false;
743 user_data_dir_ = chrome::GetUserDataDir(parameters()); 750 user_data_dir_ = chrome::GetUserDataDir(parameters());
744 751
745 // Whether this is First Run. |do_first_run_tasks_| should be prefered to this 752 // Whether this is First Run. |do_first_run_tasks_| should be prefered to this
746 // unless the desire is actually to know whether this is really First Run 753 // unless the desire is actually to know whether this is really First Run
747 // (i.e., even if --no-first-run is passed). 754 // (i.e., even if --no-first-run is passed).
748 bool is_first_run = false; 755 bool is_first_run = false;
749 // Android's first run is done in Java instead of native. 756 // Android's first run is done in Java instead of native.
750 #if !defined(OS_ANDROID) 757 #if !defined(OS_ANDROID)
751 process_singleton_.reset(new ChromeProcessSingleton( 758 process_singleton_.reset(new ChromeProcessSingleton(
752 user_data_dir_, base::Bind(&ProcessSingletonNotificationCallback))); 759 user_data_dir_, base::Bind(&ProcessSingletonOperationCallback)));
753 760
754 bool force_first_run = 761 bool force_first_run =
755 parsed_command_line().HasSwitch(switches::kForceFirstRun); 762 parsed_command_line().HasSwitch(switches::kForceFirstRun);
756 bool force_skip_first_run_tasks = 763 bool force_skip_first_run_tasks =
757 (!force_first_run && 764 (!force_first_run &&
758 parsed_command_line().HasSwitch(switches::kNoFirstRun)); 765 parsed_command_line().HasSwitch(switches::kNoFirstRun));
759 766
760 is_first_run = 767 is_first_run =
761 (force_first_run || first_run::IsChromeFirstRun()) && 768 (force_first_run || first_run::IsChromeFirstRun()) &&
762 !ProfileManager::IsImportProcess(parsed_command_line()); 769 !ProfileManager::IsImportProcess(parsed_command_line());
(...skipping 233 matching lines...) Expand 10 before | Expand all | Expand 10 after
996 #endif 1003 #endif
997 1004
998 for (size_t i = 0; i < chrome_extra_parts_.size(); ++i) 1005 for (size_t i = 0; i < chrome_extra_parts_.size(); ++i)
999 chrome_extra_parts_[i]->PostBrowserStart(); 1006 chrome_extra_parts_[i]->PostBrowserStart();
1000 #if !defined(OS_ANDROID) 1007 #if !defined(OS_ANDROID)
1001 // Allow ProcessSingleton to process messages. 1008 // Allow ProcessSingleton to process messages.
1002 process_singleton_->Unlock(); 1009 process_singleton_->Unlock();
1003 #endif 1010 #endif
1004 } 1011 }
1005 1012
1013 class CaptureOperationOutput {
1014 public:
1015 CaptureOperationOutput()
1016 : exit_code_(new base::RefCountedData<int>(INT_MAX)) {}
1017
1018 int exit_code() { return exit_code_->data; }
1019
1020 scoped_ptr<OperationOutput> Wrap(scoped_ptr<OperationOutput> wrapped) {
1021 return scoped_ptr<OperationOutput>(new Wrapper(wrapped.Pass(), exit_code_));
1022 }
1023
1024 private:
1025 class Wrapper : public OperationOutput {
1026 public:
1027 Wrapper(scoped_ptr<OperationOutput> wrapped,
1028 const scoped_refptr<base::RefCountedData<int> >& exit_code)
1029 : wrapped_(wrapped.Pass()),
1030 exit_code_(exit_code) {
1031 }
1032
1033 // OperationOutput implementation.
1034 virtual bool Write(const char* data, unsigned int length) OVERRIDE {
1035 if (wrapped_)
1036 return wrapped_->Write(data, length);
1037 return true;
1038 }
1039
1040 private:
1041 virtual bool SetExitCode(unsigned int exit_code) OVERRIDE {
1042 bool success = true;
1043 if (wrapped_)
1044 success = OperationOutput::Complete(wrapped_.Pass(), exit_code);
1045 if (success)
1046 exit_code_->data = exit_code;
1047 return success;
1048 }
1049 scoped_ptr<OperationOutput> wrapped_;
1050 scoped_refptr<base::RefCountedData<int> > exit_code_;
1051
1052 DISALLOW_COPY_AND_ASSIGN(Wrapper);
1053 };
1054
1055 scoped_refptr<base::RefCountedData<int> > exit_code_;
1056
1057 DISALLOW_COPY_AND_ASSIGN(CaptureOperationOutput);
1058 };
1059
1006 #if !defined(OS_ANDROID) 1060 #if !defined(OS_ANDROID)
1007 void ChromeBrowserMainParts::RunPageCycler() { 1061 void ChromeBrowserMainParts::RunPageCycler() {
1008 CommandLine* command_line = CommandLine::ForCurrentProcess(); 1062 CommandLine* command_line = CommandLine::ForCurrentProcess();
1009 // We assume a native desktop for tests, but we will need to find a way to 1063 // We assume a native desktop for tests, but we will need to find a way to
1010 // get the proper host desktop type once we start running these tests in ASH. 1064 // get the proper host desktop type once we start running these tests in ASH.
1011 Browser* browser = chrome::FindBrowserWithProfile( 1065 Browser* browser = chrome::FindBrowserWithProfile(
1012 profile_, chrome::HOST_DESKTOP_TYPE_NATIVE); 1066 profile_, chrome::HOST_DESKTOP_TYPE_NATIVE);
1013 DCHECK(browser); 1067 DCHECK(browser);
1014 PageCycler* page_cycler = NULL; 1068 PageCycler* page_cycler = NULL;
1015 base::FilePath input_file = 1069 base::FilePath input_file =
(...skipping 430 matching lines...) Expand 10 before | Expand all | Expand 10 after
1446 #endif 1500 #endif
1447 1501
1448 PreBrowserStart(); 1502 PreBrowserStart();
1449 1503
1450 // Instantiate the notification UI manager, as this triggers a perf timer 1504 // Instantiate the notification UI manager, as this triggers a perf timer
1451 // used to measure startup time. TODO(stevenjb): Figure out what is actually 1505 // used to measure startup time. TODO(stevenjb): Figure out what is actually
1452 // triggering the timer and call that explicitly in the approprate place. 1506 // triggering the timer and call that explicitly in the approprate place.
1453 // http://crbug.com/105065. 1507 // http://crbug.com/105065.
1454 browser_process_->notification_ui_manager(); 1508 browser_process_->notification_ui_manager();
1455 1509
1510 CaptureOperationOutput capture_output;
1511
1456 #if !defined(OS_ANDROID) 1512 #if !defined(OS_ANDROID)
1457 // Most general initialization is behind us, but opening a 1513 // Most general initialization is behind us, but opening a
1458 // tab and/or session restore and such is still to be done. 1514 // tab and/or session restore and such is still to be done.
1459 base::TimeTicks browser_open_start = base::TimeTicks::Now(); 1515 base::TimeTicks browser_open_start = base::TimeTicks::Now();
1460 1516
1461 // We are in regular browser boot sequence. Open initial tabs and enter the 1517 // We are in regular browser boot sequence. Open initial tabs and enter the
1462 // main message loop. 1518 // main message loop.
1463 int result_code; 1519
1464 #if defined(OS_CHROMEOS) 1520 #if defined(OS_CHROMEOS)
1465 // On ChromeOS multiple profiles doesn't apply, and will break if we load 1521 // On ChromeOS multiple profiles doesn't apply, and will break if we load
1466 // them this early as the cryptohome hasn't yet been mounted (which happens 1522 // them this early as the cryptohome hasn't yet been mounted (which happens
1467 // only once we log in. 1523 // only once we log in.
1468 std::vector<Profile*> last_opened_profiles; 1524 std::vector<Profile*> last_opened_profiles;
1469 #else 1525 #else
1470 std::vector<Profile*> last_opened_profiles = 1526 std::vector<Profile*> last_opened_profiles =
1471 g_browser_process->profile_manager()->GetLastOpenedProfiles(); 1527 g_browser_process->profile_manager()->GetLastOpenedProfiles();
1472 #endif 1528 #endif
1473 1529
1474 if (!parsed_command_line().HasSwitch(switches::kDisableComponentUpdate)) 1530 if (!parsed_command_line().HasSwitch(switches::kDisableComponentUpdate))
1475 RegisterComponentsForUpdate(parsed_command_line()); 1531 RegisterComponentsForUpdate(parsed_command_line());
1476 1532
1477 if (browser_creator_->Start(parsed_command_line(), base::FilePath(), 1533 if (browser_creator_->Start(
1478 profile_, last_opened_profiles, &result_code)) { 1534 parsed_command_line(), base::FilePath(),
1535 profile_, last_opened_profiles,
1536 capture_output.Wrap(
1537 OperationOutput::Create(parsed_command_line())))) {
1479 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS)) 1538 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS))
1480 // Initialize autoupdate timer. Timer callback costs basically nothing 1539 // Initialize autoupdate timer. Timer callback costs basically nothing
1481 // when browser is not in persistent mode, so it's OK to let it ride on 1540 // when browser is not in persistent mode, so it's OK to let it ride on
1482 // the main thread. This needs to be done here because we don't want 1541 // the main thread. This needs to be done here because we don't want
1483 // to start the timer when Chrome is run inside a test harness. 1542 // to start the timer when Chrome is run inside a test harness.
1484 browser_process_->StartAutoupdateTimer(); 1543 browser_process_->StartAutoupdateTimer();
1485 #endif 1544 #endif
1486 1545
1487 #if defined(OS_LINUX) && !defined(OS_CHROMEOS) 1546 #if defined(OS_LINUX) && !defined(OS_CHROMEOS)
1488 // On Linux, the running exe will be updated if an upgrade becomes 1547 // On Linux, the running exe will be updated if an upgrade becomes
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
1542 if (parameters().ui_task) { 1601 if (parameters().ui_task) {
1543 // We end the startup timer here if we have parameters to run, because we 1602 // We end the startup timer here if we have parameters to run, because we
1544 // never start to run the main loop (where we normally stop the timer). 1603 // never start to run the main loop (where we normally stop the timer).
1545 startup_timer_->SignalStartupComplete( 1604 startup_timer_->SignalStartupComplete(
1546 performance_monitor::StartupTimer::STARTUP_TEST); 1605 performance_monitor::StartupTimer::STARTUP_TEST);
1547 parameters().ui_task->Run(); 1606 parameters().ui_task->Run();
1548 delete parameters().ui_task; 1607 delete parameters().ui_task;
1549 run_message_loop_ = false; 1608 run_message_loop_ = false;
1550 } 1609 }
1551 1610
1552 return result_code_; 1611 return capture_output.exit_code();
1553 } 1612 }
1554 1613
1555 bool ChromeBrowserMainParts::MainMessageLoopRun(int* result_code) { 1614 bool ChromeBrowserMainParts::MainMessageLoopRun(int* result_code) {
1556 #if defined(OS_ANDROID) 1615 #if defined(OS_ANDROID)
1557 // Chrome on Android does not use default MessageLoop. It has its own 1616 // Chrome on Android does not use default MessageLoop. It has its own
1558 // Android specific MessageLoop 1617 // Android specific MessageLoop
1559 NOTREACHED(); 1618 NOTREACHED();
1560 return true; 1619 return true;
1561 #else 1620 #else
1562 // Set the result code set in PreMainMessageLoopRun or set above. 1621 // Set the result code set in PreMainMessageLoopRun or set above.
(...skipping 169 matching lines...) Expand 10 before | Expand all | Expand 10 after
1732 if (base::win::GetVersion() <= base::win::VERSION_XP) 1791 if (base::win::GetVersion() <= base::win::VERSION_XP)
1733 uma_name += "_XP"; 1792 uma_name += "_XP";
1734 1793
1735 uma_name += "_PreRead_"; 1794 uma_name += "_PreRead_";
1736 uma_name += pre_read_percentage; 1795 uma_name += pre_read_percentage;
1737 AddPreReadHistogramTime(uma_name.c_str(), time); 1796 AddPreReadHistogramTime(uma_name.c_str(), time);
1738 } 1797 }
1739 #endif 1798 #endif
1740 #endif 1799 #endif
1741 } 1800 }
OLDNEW
« no previous file with comments | « apps/apps.gypi ('k') | chrome/browser/chrome_process_singleton.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698