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

Unified Diff: chrome/install_static/product_install_details.cc

Issue 2487783002: Make Crashpad use the user data dir, rather than always default location (Closed)
Patch Set: . Created 4 years, 1 month 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 side-by-side diff with in-line comments
Download patch
Index: chrome/install_static/product_install_details.cc
diff --git a/chrome/install_static/product_install_details.cc b/chrome/install_static/product_install_details.cc
index 81009b3882792fad860f8d36df918a30f415439a..5ccd1c71bce57eaa2e4bc8ef6b01f078f1a8dcea 100644
--- a/chrome/install_static/product_install_details.cc
+++ b/chrome/install_static/product_install_details.cc
@@ -11,6 +11,7 @@
#include "chrome/install_static/install_modes.h"
#include "chrome/install_static/install_util.h"
+#include "chrome/install_static/policy_path_parser.h"
#include "chrome_elf/nt_registry/nt_registry.h"
namespace install_static {
@@ -38,6 +39,54 @@ const InstallConstants* FindInstallMode(const std::wstring& suffix) {
return &kInstallModes[0];
}
+// Retrieves a registry policy for the user data directory from the registry, if
+// one is set. If there's none set in either HKLM or HKCU, |user_data_dir| will
+// be unmodified.
+void GetUserDataDirFromRegistryPolicyIfSet(std::wstring* user_data_dir,
+ const InstallDetails& details) {
+ assert(user_data_dir);
+ std::wstring policies_path = L"SOFTWARE\\Policies\\";
+ AppendChromeInstallSubDirectory(&policies_path, false /* !include_suffix */,
+ details);
+
+ std::wstring value;
+
+ constexpr wchar_t kUserDataDirRegistryKeyName[] = L"UserDataDir";
+
+ // First, try HKLM.
+ if (nt::QueryRegValueSZ(nt::HKLM, nt::NONE, policies_path.c_str(),
+ kUserDataDirRegistryKeyName, &value)) {
grt (UTC plus 2) 2016/11/22 11:37:09 nit: indentation
scottmg 2016/11/22 17:16:07 Done.
+ *user_data_dir = ExpandPathVariables(value);
grt (UTC plus 2) 2016/11/22 11:37:09 hmm. this is going to be called from within chrome
scottmg 2016/11/22 17:16:07 Yup, $#@#! I was thinking it would be ok after ht
scottmg 2016/11/22 20:40:41 Wow, yeah, I suck. :( Sigh. This has to be initial
grt (UTC plus 2) 2016/11/22 21:06:58 Does this mean that the user data dir will be comp
+ return;
+ }
+
+ // Second, try HKCU.
+ if (nt::QueryRegValueSZ(nt::HKCU, nt::NONE, policies_path.c_str(),
+ kUserDataDirRegistryKeyName, &value)) {
+ *user_data_dir = ExpandPathVariables(value);
+ return;
+ }
+}
+
+std::wstring MakeAbsoluteFilePath(const std::wstring& input) {
+ wchar_t file_path[MAX_PATH];
+ if (!_wfullpath(file_path, input.c_str(), _countof(file_path)))
+ return std::wstring();
+ return file_path;
+}
+
+// The same as GetUserDataDirectory(), but directly queries the global command
+// line object for the --user-data-dir flag. This is the more commonly used
+// function, where GetUserDataDirectory() is used primiarily for testing.
+bool GetUserDataDirectoryUsingProcessCommandLine(
+ const InstallDetails& details,
+ std::wstring* result,
+ std::wstring* invalid_supplied_directory) {
+ return GetUserDataDirectory(
+ GetSwitchValueFromCommandLine(::GetCommandLine(), kUserDataDirSwitch),
+ details, result, invalid_supplied_directory);
+}
+
} // namespace
void InitializeProductDetailsForPrimaryModule() {
@@ -127,6 +176,67 @@ bool IsMultiInstall(const InstallConstants& mode, bool system_level) {
args.find(L"--multi-install") != std::wstring::npos;
}
+bool GetDefaultUserDataDirectory(const InstallDetails& details,
+ std::wstring* result) {
+ // This environment variable should be set on Windows Vista and later
+ // (https://msdn.microsoft.com/library/windows/desktop/dd378457.aspx).
+ std::wstring user_data_dir = GetEnvironmentString16(L"LOCALAPPDATA");
+
+ if (user_data_dir.empty()) {
+ // LOCALAPPDATA was not set; fallback to the temporary files path.
+ DWORD size = ::GetTempPath(0, nullptr);
+ if (!size)
+ return false;
+ user_data_dir.resize(size + 1);
+ size = ::GetTempPath(size + 1, &user_data_dir[0]);
+ if (!size || size >= user_data_dir.size())
+ return false;
+ user_data_dir.resize(size);
+ }
+
+ result->swap(user_data_dir);
+ if ((*result)[result->length() - 1] != L'\\')
+ result->push_back(L'\\');
+ AppendChromeInstallSubDirectory(result, true /* include_suffix */, details);
+ result->push_back(L'\\');
+ constexpr wchar_t kUserDataDirname[] = L"User Data";
grt (UTC plus 2) 2016/11/22 11:37:09 nit: inline the literal below?
scottmg 2016/11/22 17:16:07 Done.
+ result->append(kUserDataDirname);
+ return true;
+}
+
+bool GetUserDataDirectory(const std::wstring& user_data_dir_from_command_line,
+ const InstallDetails& details,
+ std::wstring* result,
+ std::wstring* invalid_supplied_directory) {
+ std::wstring user_data_dir = user_data_dir_from_command_line;
+
+ GetUserDataDirFromRegistryPolicyIfSet(&user_data_dir, details);
+
+ // On Windows, trailing separators leave Chrome in a bad state. See
+ // crbug.com/464616.
+ while (!user_data_dir.empty() &&
+ (user_data_dir.back() == '\\' || user_data_dir.back() == '/')) {
+ user_data_dir.pop_back();
+ }
+
+ bool got_valid_directory =
+ !user_data_dir.empty() && RecursiveDirectoryCreate(user_data_dir);
+ if (!got_valid_directory) {
+ *invalid_supplied_directory = user_data_dir;
+ got_valid_directory = GetDefaultUserDataDirectory(details, &user_data_dir);
+ }
+
+ // The Chrome implementation CHECKs() here in the browser process. We
+ // don't as this function is used to initialize crash reporting, so
+ // we would get no report of this failure.
+ assert(got_valid_directory);
+ if (!got_valid_directory)
+ return false;
+
+ *result = MakeAbsoluteFilePath(user_data_dir);
+ return true;
+}
+
std::unique_ptr<PrimaryInstallDetails> MakeProductDetails(
const std::wstring& exe_path) {
std::unique_ptr<PrimaryInstallDetails> details(new PrimaryInstallDetails());
@@ -142,6 +252,13 @@ std::unique_ptr<PrimaryInstallDetails> MakeProductDetails(
details->set_multi_install(multi_install);
details->set_channel(DetermineChannel(*mode, system_level, multi_install));
+ std::wstring user_data_dir, invalid_user_data_dir;
+ GetUserDataDirectoryUsingProcessCommandLine(*details, &user_data_dir,
grt (UTC plus 2) 2016/11/22 11:37:09 rather than passing a partially-constructed Instal
scottmg 2016/11/22 17:16:07 Done.
+ &invalid_user_data_dir);
+ details->set_user_data_dir(user_data_dir);
+ if (!invalid_user_data_dir.empty())
+ details->set_invalid_user_data_dir(invalid_user_data_dir);
+
return details;
}

Powered by Google App Engine
This is Rietveld 408576698