summaryrefslogtreecommitdiffstats
path: root/chrome/browser/shell_integration_linux.cc
diff options
context:
space:
mode:
Diffstat (limited to 'chrome/browser/shell_integration_linux.cc')
-rw-r--r--chrome/browser/shell_integration_linux.cc359
1 files changed, 176 insertions, 183 deletions
diff --git a/chrome/browser/shell_integration_linux.cc b/chrome/browser/shell_integration_linux.cc
index c521d292..4e540b2 100644
--- a/chrome/browser/shell_integration_linux.cc
+++ b/chrome/browser/shell_integration_linux.cc
@@ -55,11 +55,9 @@
using content::BrowserThread;
-namespace {
+namespace shell_integration {
-// The Categories for the App Launcher desktop shortcut. Should be the same as
-// the Chrome desktop shortcut, so they are in the same sub-menu.
-const char kAppListCategories[] = "Network;WebBrowser;";
+namespace {
// Helper to launch xdg scripts. We don't want them to ask any questions on the
// terminal etc. The function returns true if the utility launches and exits
@@ -87,6 +85,174 @@ bool LaunchXdgUtility(const std::vector<std::string>& argv, int* exit_code) {
return process.WaitForExit(exit_code);
}
+const char kXdgSettings[] = "xdg-settings";
+const char kXdgSettingsDefaultBrowser[] = "default-web-browser";
+const char kXdgSettingsDefaultSchemeHandler[] = "default-url-scheme-handler";
+
+// Utility function to get the path to the version of a script shipped with
+// Chrome. |script| gives the name of the script. |chrome_version| returns the
+// path to the Chrome version of the script, and the return value of the
+// function is true if the function is successful and the Chrome version is
+// not the script found on the PATH.
+bool GetChromeVersionOfScript(const std::string& script,
+ std::string* chrome_version) {
+ // Get the path to the Chrome version.
+ base::FilePath chrome_dir;
+ if (!PathService::Get(base::DIR_EXE, &chrome_dir))
+ return false;
+
+ base::FilePath chrome_version_path = chrome_dir.Append(script);
+ *chrome_version = chrome_version_path.value();
+
+ // Check if this is different to the one on path.
+ std::vector<std::string> argv;
+ argv.push_back("which");
+ argv.push_back(script);
+ std::string path_version;
+ if (base::GetAppOutput(base::CommandLine(argv), &path_version)) {
+ // Remove trailing newline
+ path_version.erase(path_version.length() - 1, 1);
+ base::FilePath path_version_path(path_version);
+ return (chrome_version_path != path_version_path);
+ }
+ return false;
+}
+
+// Value returned by xdg-settings if it can't understand our request.
+const int EXIT_XDG_SETTINGS_SYNTAX_ERROR = 1;
+
+// We delegate the difficulty of setting the default browser and default url
+// scheme handler in Linux desktop environments to an xdg utility, xdg-settings.
+
+// When calling this script we first try to use the script on PATH. If that
+// fails we then try to use the script that we have included. This gives
+// scripts on the system priority over ours, as distribution vendors may have
+// tweaked the script, but still allows our copy to be used if the script on the
+// system fails, as the system copy may be missing capabilities of the Chrome
+// copy.
+
+// If |protocol| is empty this function sets Chrome as the default browser,
+// otherwise it sets Chrome as the default handler application for |protocol|.
+bool SetDefaultWebClient(const std::string& protocol) {
+#if defined(OS_CHROMEOS)
+ return true;
+#else
+ scoped_ptr<base::Environment> env(base::Environment::Create());
+
+ std::vector<std::string> argv;
+ argv.push_back(kXdgSettings);
+ argv.push_back("set");
+ if (protocol.empty()) {
+ argv.push_back(kXdgSettingsDefaultBrowser);
+ } else {
+ argv.push_back(kXdgSettingsDefaultSchemeHandler);
+ argv.push_back(protocol);
+ }
+ argv.push_back(shell_integration_linux::GetDesktopName(env.get()));
+
+ int exit_code;
+ bool ran_ok = LaunchXdgUtility(argv, &exit_code);
+ if (ran_ok && exit_code == EXIT_XDG_SETTINGS_SYNTAX_ERROR) {
+ if (GetChromeVersionOfScript(kXdgSettings, &argv[0])) {
+ ran_ok = LaunchXdgUtility(argv, &exit_code);
+ }
+ }
+
+ return ran_ok && exit_code == EXIT_SUCCESS;
+#endif
+}
+
+// If |protocol| is empty this function checks if Chrome is the default browser,
+// otherwise it checks if Chrome is the default handler application for
+// |protocol|.
+DefaultWebClientState GetIsDefaultWebClient(const std::string& protocol) {
+#if defined(OS_CHROMEOS)
+ return UNKNOWN_DEFAULT;
+#else
+ base::ThreadRestrictions::AssertIOAllowed();
+
+ scoped_ptr<base::Environment> env(base::Environment::Create());
+
+ std::vector<std::string> argv;
+ argv.push_back(kXdgSettings);
+ argv.push_back("check");
+ if (protocol.empty()) {
+ argv.push_back(kXdgSettingsDefaultBrowser);
+ } else {
+ argv.push_back(kXdgSettingsDefaultSchemeHandler);
+ argv.push_back(protocol);
+ }
+ argv.push_back(shell_integration_linux::GetDesktopName(env.get()));
+
+ std::string reply;
+ int success_code;
+ bool ran_ok = base::GetAppOutputWithExitCode(base::CommandLine(argv), &reply,
+ &success_code);
+ if (ran_ok && success_code == EXIT_XDG_SETTINGS_SYNTAX_ERROR) {
+ if (GetChromeVersionOfScript(kXdgSettings, &argv[0])) {
+ ran_ok = base::GetAppOutputWithExitCode(base::CommandLine(argv), &reply,
+ &success_code);
+ }
+ }
+
+ if (!ran_ok || success_code != EXIT_SUCCESS) {
+ // xdg-settings failed: we can't determine or set the default browser.
+ return UNKNOWN_DEFAULT;
+ }
+
+ // Allow any reply that starts with "yes".
+ return (reply.find("yes") == 0) ? IS_DEFAULT : NOT_DEFAULT;
+#endif
+}
+
+} // namespace
+
+bool SetAsDefaultBrowser() {
+ return SetDefaultWebClient(std::string());
+}
+
+bool SetAsDefaultProtocolClient(const std::string& protocol) {
+ return SetDefaultWebClient(protocol);
+}
+
+DefaultWebClientSetPermission CanSetAsDefaultBrowser() {
+ return SET_DEFAULT_UNATTENDED;
+}
+
+base::string16 GetApplicationNameForProtocol(const GURL& url) {
+ return base::ASCIIToUTF16("xdg-open");
+}
+
+DefaultWebClientState GetDefaultBrowser() {
+ return GetIsDefaultWebClient(std::string());
+}
+
+bool IsFirefoxDefaultBrowser() {
+ std::vector<std::string> argv;
+ argv.push_back(kXdgSettings);
+ argv.push_back("get");
+ argv.push_back(kXdgSettingsDefaultBrowser);
+
+ std::string browser;
+ // We don't care about the return value here.
+ base::GetAppOutput(base::CommandLine(argv), &browser);
+ return browser.find("irefox") != std::string::npos;
+}
+
+DefaultWebClientState IsDefaultProtocolClient(const std::string& protocol) {
+ return GetIsDefaultWebClient(protocol);
+}
+
+} // namespace shell_integration
+
+namespace shell_integration_linux {
+
+namespace {
+
+// The Categories for the App Launcher desktop shortcut. Should be the same as
+// the Chrome desktop shortcut, so they are in the same sub-menu.
+const char kAppListCategories[] = "Network;WebBrowser;";
+
std::string CreateShortcutIcon(const gfx::ImageFamily& icon_images,
const base::FilePath& shortcut_filename) {
if (icon_images.empty())
@@ -133,7 +299,7 @@ std::string CreateShortcutIcon(const gfx::ImageFamily& icon_images,
argv.push_back(temp_file_path.value());
argv.push_back(icon_name);
int exit_code;
- if (!LaunchXdgUtility(argv, &exit_code) || exit_code) {
+ if (!shell_integration::LaunchXdgUtility(argv, &exit_code) || exit_code) {
LOG(WARNING) << "Could not install icon " << icon_name << ".png at size "
<< width << ".";
}
@@ -232,7 +398,7 @@ bool CreateShortcutInApplicationsMenu(const base::FilePath& shortcut_filename,
argv.push_back(temp_directory_path.value());
argv.push_back(temp_file_path.value());
int exit_code;
- LaunchXdgUtility(argv, &exit_code);
+ shell_integration::LaunchXdgUtility(argv, &exit_code);
return exit_code == 0;
}
@@ -255,7 +421,7 @@ void DeleteShortcutInApplicationsMenu(
argv.push_back(directory_filename.value());
argv.push_back(shortcut_filename.value());
int exit_code;
- LaunchXdgUtility(argv, &exit_code);
+ shell_integration::LaunchXdgUtility(argv, &exit_code);
}
#if defined(USE_GLIB)
@@ -311,10 +477,6 @@ const char kDesktopEntry[] = "Desktop Entry";
const char kXdgOpenShebang[] = "#!/usr/bin/env xdg-open";
#endif
-const char kXdgSettings[] = "xdg-settings";
-const char kXdgSettingsDefaultBrowser[] = "default-web-browser";
-const char kXdgSettingsDefaultSchemeHandler[] = "default-url-scheme-handler";
-
const char kDirectoryFilename[] = "chrome-apps.directory";
#if defined(GOOGLE_CHROME_BUILD)
@@ -323,124 +485,6 @@ const char kAppListDesktopName[] = "chrome-app-list";
const char kAppListDesktopName[] = "chromium-app-list";
#endif
-// Utility function to get the path to the version of a script shipped with
-// Chrome. |script| gives the name of the script. |chrome_version| returns the
-// path to the Chrome version of the script, and the return value of the
-// function is true if the function is successful and the Chrome version is
-// not the script found on the PATH.
-bool GetChromeVersionOfScript(const std::string& script,
- std::string* chrome_version) {
- // Get the path to the Chrome version.
- base::FilePath chrome_dir;
- if (!PathService::Get(base::DIR_EXE, &chrome_dir))
- return false;
-
- base::FilePath chrome_version_path = chrome_dir.Append(script);
- *chrome_version = chrome_version_path.value();
-
- // Check if this is different to the one on path.
- std::vector<std::string> argv;
- argv.push_back("which");
- argv.push_back(script);
- std::string path_version;
- if (base::GetAppOutput(base::CommandLine(argv), &path_version)) {
- // Remove trailing newline
- path_version.erase(path_version.length() - 1, 1);
- base::FilePath path_version_path(path_version);
- return (chrome_version_path != path_version_path);
- }
- return false;
-}
-
-// Value returned by xdg-settings if it can't understand our request.
-const int EXIT_XDG_SETTINGS_SYNTAX_ERROR = 1;
-
-// We delegate the difficulty of setting the default browser and default url
-// scheme handler in Linux desktop environments to an xdg utility, xdg-settings.
-
-// When calling this script we first try to use the script on PATH. If that
-// fails we then try to use the script that we have included. This gives
-// scripts on the system priority over ours, as distribution vendors may have
-// tweaked the script, but still allows our copy to be used if the script on the
-// system fails, as the system copy may be missing capabilities of the Chrome
-// copy.
-
-// If |protocol| is empty this function sets Chrome as the default browser,
-// otherwise it sets Chrome as the default handler application for |protocol|.
-bool SetDefaultWebClient(const std::string& protocol) {
-#if defined(OS_CHROMEOS)
- return true;
-#else
- scoped_ptr<base::Environment> env(base::Environment::Create());
-
- std::vector<std::string> argv;
- argv.push_back(kXdgSettings);
- argv.push_back("set");
- if (protocol.empty()) {
- argv.push_back(kXdgSettingsDefaultBrowser);
- } else {
- argv.push_back(kXdgSettingsDefaultSchemeHandler);
- argv.push_back(protocol);
- }
- argv.push_back(shell_integration_linux::GetDesktopName(env.get()));
-
- int exit_code;
- bool ran_ok = LaunchXdgUtility(argv, &exit_code);
- if (ran_ok && exit_code == EXIT_XDG_SETTINGS_SYNTAX_ERROR) {
- if (GetChromeVersionOfScript(kXdgSettings, &argv[0])) {
- ran_ok = LaunchXdgUtility(argv, &exit_code);
- }
- }
-
- return ran_ok && exit_code == EXIT_SUCCESS;
-#endif
-}
-
-// If |protocol| is empty this function checks if Chrome is the default browser,
-// otherwise it checks if Chrome is the default handler application for
-// |protocol|.
-ShellIntegration::DefaultWebClientState GetIsDefaultWebClient(
- const std::string& protocol) {
-#if defined(OS_CHROMEOS)
- return ShellIntegration::UNKNOWN_DEFAULT;
-#else
- base::ThreadRestrictions::AssertIOAllowed();
-
- scoped_ptr<base::Environment> env(base::Environment::Create());
-
- std::vector<std::string> argv;
- argv.push_back(kXdgSettings);
- argv.push_back("check");
- if (protocol.empty()) {
- argv.push_back(kXdgSettingsDefaultBrowser);
- } else {
- argv.push_back(kXdgSettingsDefaultSchemeHandler);
- argv.push_back(protocol);
- }
- argv.push_back(shell_integration_linux::GetDesktopName(env.get()));
-
- std::string reply;
- int success_code;
- bool ran_ok = base::GetAppOutputWithExitCode(base::CommandLine(argv), &reply,
- &success_code);
- if (ran_ok && success_code == EXIT_XDG_SETTINGS_SYNTAX_ERROR) {
- if (GetChromeVersionOfScript(kXdgSettings, &argv[0])) {
- ran_ok = base::GetAppOutputWithExitCode(base::CommandLine(argv), &reply,
- &success_code);
- }
- }
-
- if (!ran_ok || success_code != EXIT_SUCCESS) {
- // xdg-settings failed: we can't determine or set the default browser.
- return ShellIntegration::UNKNOWN_DEFAULT;
- }
-
- // Allow any reply that starts with "yes".
- return (reply.find("yes") == 0) ? ShellIntegration::IS_DEFAULT :
- ShellIntegration::NOT_DEFAULT;
-#endif
-}
-
// Get the value of NoDisplay from the [Desktop Entry] section of a .desktop
// file, given in |shortcut_contents|. If the key is not found, returns false.
bool GetNoDisplayFromDesktopFile(const std::string& shortcut_contents) {
@@ -497,56 +541,6 @@ base::FilePath GetChromeExePath() {
} // namespace
-// static
-bool ShellIntegration::SetAsDefaultBrowser() {
- return SetDefaultWebClient(std::string());
-}
-
-// static
-bool ShellIntegration::SetAsDefaultProtocolClient(
- const std::string& protocol) {
- return SetDefaultWebClient(protocol);
-}
-
-// static
-ShellIntegration::DefaultWebClientSetPermission
-ShellIntegration::CanSetAsDefaultBrowser() {
- return SET_DEFAULT_UNATTENDED;
-}
-
-// static
-base::string16 ShellIntegration::GetApplicationNameForProtocol(
- const GURL& url) {
- return base::ASCIIToUTF16("xdg-open");
-}
-
-// static
-ShellIntegration::DefaultWebClientState
-ShellIntegration::GetDefaultBrowser() {
- return GetIsDefaultWebClient(std::string());
-}
-
-// static
-bool ShellIntegration::IsFirefoxDefaultBrowser() {
- std::vector<std::string> argv;
- argv.push_back(kXdgSettings);
- argv.push_back("get");
- argv.push_back(kXdgSettingsDefaultBrowser);
-
- std::string browser;
- // We don't care about the return value here.
- base::GetAppOutput(base::CommandLine(argv), &browser);
- return browser.find("irefox") != std::string::npos;
-}
-
-// static
-ShellIntegration::DefaultWebClientState
-ShellIntegration::IsDefaultProtocolClient(const std::string& protocol) {
- return GetIsDefaultWebClient(protocol);
-}
-
-namespace shell_integration_linux {
-
base::FilePath GetDataWriteLocation(base::Environment* env) {
DCHECK_CURRENTLY_ON(BrowserThread::FILE);
@@ -756,9 +750,8 @@ std::string GetDesktopFileContents(
const base::FilePath& profile_path,
const std::string& categories,
bool no_display) {
- base::CommandLine cmd_line =
- ShellIntegration::CommandLineArgsForLauncher(url, extension_id,
- profile_path);
+ base::CommandLine cmd_line = shell_integration::CommandLineArgsForLauncher(
+ url, extension_id, profile_path);
cmd_line.SetProgram(chrome_exe_path);
return GetDesktopFileContentsForCommand(cmd_line, app_name, url, title,
icon_name, categories, no_display);
@@ -951,7 +944,7 @@ bool CreateDesktopShortcut(
case web_app::APP_MENU_LOCATION_SUBDIR_CHROMEAPPS:
directory_filename = base::FilePath(kDirectoryFilename);
directory_contents = GetDirectoryFileContents(
- ShellIntegration::GetAppShortcutsSubdirName(), "");
+ shell_integration::GetAppShortcutsSubdirName(), "");
break;
default:
NOTREACHED();