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

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: Line endings. Created 7 years, 9 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
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>
gab 2013/03/28 03:06:06 C-headers come after C++ headers and are usually i
erikwright (departed) 2013/04/18 17:43:04 You so crazy :) C first. http://google-styleguid
gab 2013/04/19 14:37:47 You know who I learnt to code-review from ;)!
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/cpu.h" 18 #include "base/cpu.h"
18 #include "base/debug/trace_event.h" 19 #include "base/debug/trace_event.h"
19 #include "base/file_util.h" 20 #include "base/file_util.h"
20 #include "base/files/file_path.h" 21 #include "base/files/file_path.h"
22 #include "base/memory/ref_counted.h"
21 #include "base/metrics/field_trial.h" 23 #include "base/metrics/field_trial.h"
22 #include "base/metrics/histogram.h" 24 #include "base/metrics/histogram.h"
23 #include "base/path_service.h" 25 #include "base/path_service.h"
24 #include "base/prefs/json_pref_store.h" 26 #include "base/prefs/json_pref_store.h"
25 #include "base/prefs/pref_registry_simple.h" 27 #include "base/prefs/pref_registry_simple.h"
26 #include "base/prefs/pref_service.h" 28 #include "base/prefs/pref_service.h"
27 #include "base/prefs/pref_value_store.h" 29 #include "base/prefs/pref_value_store.h"
28 #include "base/process_info.h" 30 #include "base/process_info.h"
29 #include "base/process_util.h" 31 #include "base/process_util.h"
30 #include "base/run_loop.h" 32 #include "base/run_loop.h"
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
65 #include "chrome/browser/metrics/metrics_log.h" 67 #include "chrome/browser/metrics/metrics_log.h"
66 #include "chrome/browser/metrics/metrics_service.h" 68 #include "chrome/browser/metrics/metrics_service.h"
67 #include "chrome/browser/metrics/thread_watcher.h" 69 #include "chrome/browser/metrics/thread_watcher.h"
68 #include "chrome/browser/metrics/tracking_synchronizer.h" 70 #include "chrome/browser/metrics/tracking_synchronizer.h"
69 #include "chrome/browser/metrics/variations/variations_service.h" 71 #include "chrome/browser/metrics/variations/variations_service.h"
70 #include "chrome/browser/nacl_host/nacl_process_host.h" 72 #include "chrome/browser/nacl_host/nacl_process_host.h"
71 #include "chrome/browser/net/chrome_net_log.h" 73 #include "chrome/browser/net/chrome_net_log.h"
72 #include "chrome/browser/net/crl_set_fetcher.h" 74 #include "chrome/browser/net/crl_set_fetcher.h"
73 #include "chrome/browser/notifications/desktop_notification_service.h" 75 #include "chrome/browser/notifications/desktop_notification_service.h"
74 #include "chrome/browser/notifications/desktop_notification_service_factory.h" 76 #include "chrome/browser/notifications/desktop_notification_service_factory.h"
77 #include "chrome/browser/operation_output.h"
75 #include "chrome/browser/page_cycler/page_cycler.h" 78 #include "chrome/browser/page_cycler/page_cycler.h"
76 #include "chrome/browser/performance_monitor/performance_monitor.h" 79 #include "chrome/browser/performance_monitor/performance_monitor.h"
77 #include "chrome/browser/performance_monitor/startup_timer.h" 80 #include "chrome/browser/performance_monitor/startup_timer.h"
78 #include "chrome/browser/plugins/plugin_prefs.h" 81 #include "chrome/browser/plugins/plugin_prefs.h"
79 #include "chrome/browser/policy/policy_service.h" 82 #include "chrome/browser/policy/policy_service.h"
80 #include "chrome/browser/prefs/chrome_pref_service_factory.h" 83 #include "chrome/browser/prefs/chrome_pref_service_factory.h"
81 #include "chrome/browser/prefs/command_line_pref_store.h" 84 #include "chrome/browser/prefs/command_line_pref_store.h"
82 #include "chrome/browser/prefs/scoped_user_pref_update.h" 85 #include "chrome/browser/prefs/scoped_user_pref_update.h"
83 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service.h" 86 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service.h"
84 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service_factory. h" 87 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service_factory. h"
(...skipping 403 matching lines...) Expand 10 before | Expand all | Expand 10 after
488 // network. 491 // network.
489 if (!command_line.HasSwitch(switches::kDisableCRLSets)) 492 if (!command_line.HasSwitch(switches::kDisableCRLSets))
490 g_browser_process->crl_set_fetcher()->StartInitialLoad(cus); 493 g_browser_process->crl_set_fetcher()->StartInitialLoad(cus);
491 494
492 RegisterPnaclComponent(cus, command_line); 495 RegisterPnaclComponent(cus, command_line);
493 496
494 cus->Start(); 497 cus->Start();
495 } 498 }
496 499
497 #if !defined(OS_ANDROID) 500 #if !defined(OS_ANDROID)
498 bool ProcessSingletonNotificationCallback( 501 bool ProcessSingletonOperationCallback(
499 const CommandLine& command_line, 502 const CommandLine& command_line,
500 const base::FilePath& current_directory) { 503 const base::FilePath& current_directory,
504 scoped_ptr<OperationOutput> operation_output) {
501 // Drop the request if the browser process is already in shutdown path. 505 // Drop the request if the browser process is already in shutdown path.
502 if (!g_browser_process || g_browser_process->IsShuttingDown()) 506 if (!g_browser_process || g_browser_process->IsShuttingDown())
503 return false; 507 return false;
504 508
505 g_browser_process->PlatformSpecificCommandLineProcessing(command_line); 509 g_browser_process->PlatformSpecificCommandLineProcessing(command_line);
506 510
507 // TODO(erikwright): Consider removing this - AFAIK it is no longer used. 511 // TODO(erikwright): Consider removing this - AFAIK it is no longer used.
508 // Handle the --uninstall-extension startup action. This needs to done here in 512 // Handle the --uninstall-extension startup action. This needs to done here in
509 // the process that is running with the target profile, otherwise the 513 // the process that is running with the target profile, otherwise the
510 // uninstall will fail to unload and remove all components. 514 // uninstall will fail to unload and remove all components.
(...skipping 13 matching lines...) Expand all
524 extension_startup_helper.UninstallExtension(command_line, profile); 528 extension_startup_helper.UninstallExtension(command_line, profile);
525 return true; 529 return true;
526 } 530 }
527 531
528 base::FilePath user_data_dir = 532 base::FilePath user_data_dir =
529 g_browser_process->profile_manager()->user_data_dir(); 533 g_browser_process->profile_manager()->user_data_dir();
530 base::FilePath startup_profile_dir = 534 base::FilePath startup_profile_dir =
531 GetStartupProfilePath(user_data_dir, command_line); 535 GetStartupProfilePath(user_data_dir, command_line);
532 536
533 StartupBrowserCreator::ProcessCommandLineAlreadyRunning( 537 StartupBrowserCreator::ProcessCommandLineAlreadyRunning(
534 command_line, current_directory, startup_profile_dir); 538 command_line,
539 current_directory,
540 startup_profile_dir,
541 operation_output.Pass());
535 return true; 542 return true;
536 } 543 }
537 #endif 544 #endif
538 545
539 void LaunchDevToolsHandlerIfNeeded(Profile* profile, 546 void LaunchDevToolsHandlerIfNeeded(Profile* profile,
540 const CommandLine& command_line) { 547 const CommandLine& command_line) {
541 if (command_line.HasSwitch(::switches::kRemoteDebuggingPort)) { 548 if (command_line.HasSwitch(::switches::kRemoteDebuggingPort)) {
542 std::string port_str = 549 std::string port_str =
543 command_line.GetSwitchValueASCII(::switches::kRemoteDebuggingPort); 550 command_line.GetSwitchValueASCII(::switches::kRemoteDebuggingPort);
544 int port; 551 int port;
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
605 const content::MainFunctionParams& parameters) 612 const content::MainFunctionParams& parameters)
606 : parameters_(parameters), 613 : parameters_(parameters),
607 parsed_command_line_(parameters.command_line), 614 parsed_command_line_(parameters.command_line),
608 result_code_(content::RESULT_CODE_NORMAL_EXIT), 615 result_code_(content::RESULT_CODE_NORMAL_EXIT),
609 startup_watcher_(new StartupTimeBomb()), 616 startup_watcher_(new StartupTimeBomb()),
610 shutdown_watcher_(new ShutdownWatcherHelper()), 617 shutdown_watcher_(new ShutdownWatcherHelper()),
611 startup_timer_(new performance_monitor::StartupTimer()), 618 startup_timer_(new performance_monitor::StartupTimer()),
612 browser_field_trials_(parameters.command_line), 619 browser_field_trials_(parameters.command_line),
613 #if !defined(OS_ANDROID) 620 #if !defined(OS_ANDROID)
614 process_singleton_lock_( 621 process_singleton_lock_(
615 base::Bind(&ProcessSingletonNotificationCallback)), 622 base::Bind(&ProcessSingletonOperationCallback)),
616 modal_dialog_lock_(process_singleton_lock_.AsNotificationCallback()), 623 modal_dialog_lock_(process_singleton_lock_.AsNotificationCallback()),
617 #endif 624 #endif
618 record_search_engine_(false), 625 record_search_engine_(false),
619 translate_manager_(NULL), 626 translate_manager_(NULL),
620 profile_(NULL), 627 profile_(NULL),
621 run_message_loop_(true), 628 run_message_loop_(true),
622 notify_result_(ProcessSingleton::PROCESS_NONE), 629 notify_result_(ProcessSingleton::PROCESS_NONE),
623 do_first_run_tasks_(false), 630 do_first_run_tasks_(false),
624 local_state_(NULL), 631 local_state_(NULL),
625 restart_last_session_(false) { 632 restart_last_session_(false) {
(...skipping 446 matching lines...) Expand 10 before | Expand all | Expand 10 after
1072 #endif 1079 #endif
1073 1080
1074 for (size_t i = 0; i < chrome_extra_parts_.size(); ++i) 1081 for (size_t i = 0; i < chrome_extra_parts_.size(); ++i)
1075 chrome_extra_parts_[i]->PostBrowserStart(); 1082 chrome_extra_parts_[i]->PostBrowserStart();
1076 #if !defined(OS_ANDROID) 1083 #if !defined(OS_ANDROID)
1077 // Allow ProcessSingleton to process messages. 1084 // Allow ProcessSingleton to process messages.
1078 process_singleton_lock_.Unlock(); 1085 process_singleton_lock_.Unlock();
1079 #endif 1086 #endif
1080 } 1087 }
1081 1088
1089 class CaptureOperationOutput {
1090 public:
1091 CaptureOperationOutput()
1092 : exit_code_(new base::RefCountedData<int>(INT_MAX)) {}
1093
1094 int exit_code() { return exit_code_->data; }
1095
1096 scoped_ptr<OperationOutput> Wrap(scoped_ptr<OperationOutput> wrapped) {
1097 return scoped_ptr<OperationOutput>(new Wrapper(wrapped.Pass(), exit_code_));
1098 }
1099
1100 private:
1101 class Wrapper : public OperationOutput {
1102 public:
1103 Wrapper(scoped_ptr<OperationOutput> wrapped,
1104 const scoped_refptr<base::RefCountedData<int> >& exit_code)
1105 : wrapped_(wrapped.Pass()),
1106 exit_code_(exit_code) {
1107 }
1108
1109 // OperationOutput implementation.
1110 virtual bool Write(const char* data, unsigned int length) OVERRIDE {
1111 if (wrapped_)
1112 return wrapped_->Write(data, length);
1113 return true;
1114 }
1115
1116 private:
1117 virtual bool SetExitCode(unsigned int exit_code) OVERRIDE {
1118 bool success = true;
1119 if (wrapped_)
1120 success = OperationOutput::Complete(wrapped_.Pass(), exit_code);
1121 if (success)
1122 exit_code_->data = exit_code;
1123 return success;
1124 }
1125 scoped_ptr<OperationOutput> wrapped_;
1126 scoped_refptr<base::RefCountedData<int> > exit_code_;
1127
1128 DISALLOW_COPY_AND_ASSIGN(Wrapper);
1129 };
1130
1131 scoped_refptr<base::RefCountedData<int> > exit_code_;
1132
1133 DISALLOW_COPY_AND_ASSIGN(CaptureOperationOutput);
1134 };
1135
1082 #if !defined(OS_ANDROID) 1136 #if !defined(OS_ANDROID)
1083 void ChromeBrowserMainParts::RunPageCycler() { 1137 void ChromeBrowserMainParts::RunPageCycler() {
1084 CommandLine* command_line = CommandLine::ForCurrentProcess(); 1138 CommandLine* command_line = CommandLine::ForCurrentProcess();
1085 // We assume a native desktop for tests, but we will need to find a way to 1139 // We assume a native desktop for tests, but we will need to find a way to
1086 // get the proper host desktop type once we start running these tests in ASH. 1140 // get the proper host desktop type once we start running these tests in ASH.
1087 Browser* browser = chrome::FindBrowserWithProfile( 1141 Browser* browser = chrome::FindBrowserWithProfile(
1088 profile_, chrome::HOST_DESKTOP_TYPE_NATIVE); 1142 profile_, chrome::HOST_DESKTOP_TYPE_NATIVE);
1089 DCHECK(browser); 1143 DCHECK(browser);
1090 PageCycler* page_cycler = NULL; 1144 PageCycler* page_cycler = NULL;
1091 base::FilePath input_file = 1145 base::FilePath input_file =
(...skipping 443 matching lines...) Expand 10 before | Expand all | Expand 10 after
1535 #endif 1589 #endif
1536 1590
1537 PreBrowserStart(); 1591 PreBrowserStart();
1538 1592
1539 // Instantiate the notification UI manager, as this triggers a perf timer 1593 // Instantiate the notification UI manager, as this triggers a perf timer
1540 // used to measure startup time. TODO(stevenjb): Figure out what is actually 1594 // used to measure startup time. TODO(stevenjb): Figure out what is actually
1541 // triggering the timer and call that explicitly in the approprate place. 1595 // triggering the timer and call that explicitly in the approprate place.
1542 // http://crbug.com/105065. 1596 // http://crbug.com/105065.
1543 browser_process_->notification_ui_manager(); 1597 browser_process_->notification_ui_manager();
1544 1598
1599 CaptureOperationOutput capture_output;
1600
1545 #if !defined(OS_ANDROID) 1601 #if !defined(OS_ANDROID)
1546 // Most general initialization is behind us, but opening a 1602 // Most general initialization is behind us, but opening a
1547 // tab and/or session restore and such is still to be done. 1603 // tab and/or session restore and such is still to be done.
1548 base::TimeTicks browser_open_start = base::TimeTicks::Now(); 1604 base::TimeTicks browser_open_start = base::TimeTicks::Now();
1549 1605
1550 // We are in regular browser boot sequence. Open initial tabs and enter the 1606 // We are in regular browser boot sequence. Open initial tabs and enter the
1551 // main message loop. 1607 // main message loop.
1552 int result_code; 1608
1553 #if defined(OS_CHROMEOS) 1609 #if defined(OS_CHROMEOS)
1554 // On ChromeOS multiple profiles doesn't apply, and will break if we load 1610 // On ChromeOS multiple profiles doesn't apply, and will break if we load
1555 // them this early as the cryptohome hasn't yet been mounted (which happens 1611 // them this early as the cryptohome hasn't yet been mounted (which happens
1556 // only once we log in. 1612 // only once we log in.
1557 std::vector<Profile*> last_opened_profiles; 1613 std::vector<Profile*> last_opened_profiles;
1558 #else 1614 #else
1559 std::vector<Profile*> last_opened_profiles = 1615 std::vector<Profile*> last_opened_profiles =
1560 g_browser_process->profile_manager()->GetLastOpenedProfiles(); 1616 g_browser_process->profile_manager()->GetLastOpenedProfiles();
1561 #endif 1617 #endif
1562 1618
1563 if (!parsed_command_line().HasSwitch(switches::kDisableComponentUpdate)) 1619 if (!parsed_command_line().HasSwitch(switches::kDisableComponentUpdate))
1564 RegisterComponentsForUpdate(parsed_command_line()); 1620 RegisterComponentsForUpdate(parsed_command_line());
1565 1621
1566 if (browser_creator_->Start(parsed_command_line(), base::FilePath(), 1622 if (browser_creator_->Start(
1567 profile_, last_opened_profiles, &result_code)) { 1623 parsed_command_line(), base::FilePath(),
1624 profile_, last_opened_profiles,
1625 capture_output.Wrap(
1626 OperationOutput::Create(parsed_command_line())))) {
1568 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS)) 1627 #if defined(OS_WIN) || (defined(OS_LINUX) && !defined(OS_CHROMEOS))
1569 // Initialize autoupdate timer. Timer callback costs basically nothing 1628 // Initialize autoupdate timer. Timer callback costs basically nothing
1570 // when browser is not in persistent mode, so it's OK to let it ride on 1629 // when browser is not in persistent mode, so it's OK to let it ride on
1571 // the main thread. This needs to be done here because we don't want 1630 // the main thread. This needs to be done here because we don't want
1572 // to start the timer when Chrome is run inside a test harness. 1631 // to start the timer when Chrome is run inside a test harness.
1573 browser_process_->StartAutoupdateTimer(); 1632 browser_process_->StartAutoupdateTimer();
1574 #endif 1633 #endif
1575 1634
1576 #if defined(OS_LINUX) && !defined(OS_CHROMEOS) 1635 #if defined(OS_LINUX) && !defined(OS_CHROMEOS)
1577 // On Linux, the running exe will be updated if an upgrade becomes 1636 // On Linux, the running exe will be updated if an upgrade becomes
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
1633 if (parameters().ui_task) { 1692 if (parameters().ui_task) {
1634 // We end the startup timer here if we have parameters to run, because we 1693 // We end the startup timer here if we have parameters to run, because we
1635 // never start to run the main loop (where we normally stop the timer). 1694 // never start to run the main loop (where we normally stop the timer).
1636 startup_timer_->SignalStartupComplete( 1695 startup_timer_->SignalStartupComplete(
1637 performance_monitor::StartupTimer::STARTUP_TEST); 1696 performance_monitor::StartupTimer::STARTUP_TEST);
1638 parameters().ui_task->Run(); 1697 parameters().ui_task->Run();
1639 delete parameters().ui_task; 1698 delete parameters().ui_task;
1640 run_message_loop_ = false; 1699 run_message_loop_ = false;
1641 } 1700 }
1642 1701
1643 return result_code_; 1702 return capture_output.exit_code();
1644 } 1703 }
1645 1704
1646 bool ChromeBrowserMainParts::MainMessageLoopRun(int* result_code) { 1705 bool ChromeBrowserMainParts::MainMessageLoopRun(int* result_code) {
1647 #if defined(OS_ANDROID) 1706 #if defined(OS_ANDROID)
1648 // Chrome on Android does not use default MessageLoop. It has its own 1707 // Chrome on Android does not use default MessageLoop. It has its own
1649 // Android specific MessageLoop 1708 // Android specific MessageLoop
1650 NOTREACHED(); 1709 NOTREACHED();
1651 return true; 1710 return true;
1652 #else 1711 #else
1653 // Set the result code set in PreMainMessageLoopRun or set above. 1712 // Set the result code set in PreMainMessageLoopRun or set above.
(...skipping 169 matching lines...) Expand 10 before | Expand all | Expand 10 after
1823 if (base::win::GetVersion() <= base::win::VERSION_XP) 1882 if (base::win::GetVersion() <= base::win::VERSION_XP)
1824 uma_name += "_XP"; 1883 uma_name += "_XP";
1825 1884
1826 uma_name += "_PreRead_"; 1885 uma_name += "_PreRead_";
1827 uma_name += pre_read_percentage; 1886 uma_name += pre_read_percentage;
1828 AddPreReadHistogramTime(uma_name.c_str(), time); 1887 AddPreReadHistogramTime(uma_name.c_str(), time);
1829 } 1888 }
1830 #endif 1889 #endif
1831 #endif 1890 #endif
1832 } 1891 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698