[tor-commits] [tor-messenger-build/updater] Add patch for #14631
sukhbir at torproject.org
sukhbir at torproject.org
Fri Jul 29 17:20:47 UTC 2016
commit d4f35015683bedf07194f3982e080641eb0ff27f
Author: Sukhbir Singh <sukhbir at torproject.org>
Date: Mon Jul 18 12:40:15 2016 -0400
Add patch for #14631
---
...Improve-profile-access-bug-14631-first.mozpatch | 246 +++++++++++++++++++++
...mprove-profile-access-bug-14631-second.mozpatch | 182 +++++++++++++++
2 files changed, 428 insertions(+)
diff --git a/projects/instantbird/Improve-profile-access-bug-14631-first.mozpatch b/projects/instantbird/Improve-profile-access-bug-14631-first.mozpatch
new file mode 100644
index 0000000..7a9ad68
--- /dev/null
+++ b/projects/instantbird/Improve-profile-access-bug-14631-first.mozpatch
@@ -0,0 +1,246 @@
+commit 5aae044b37579dc1c95b195084bcfcdaed352545
+Author: Kathy Brade <brade at pearlcrescent.com>
+Date: Tue Feb 24 13:50:23 2015 -0500
+
+ Bug 14631: Improve profile access error messages.
+
+ Instead of always reporting that the profile is locked, display specific
+ messages for "access denied" and "read-only file system".
+
+diff --git a/toolkit/locales/en-US/chrome/mozapps/profile/profileSelection.properties b/toolkit/locales/en-US/chrome/mozapps/profile/profileSelection.properties
+index adac95a..3cf48ff 100644
+--- a/toolkit/locales/en-US/chrome/mozapps/profile/profileSelection.properties
++++ b/toolkit/locales/en-US/chrome/mozapps/profile/profileSelection.properties
+@@ -12,6 +12,11 @@ restartMessageUnlocker=%S is already running, but is not responding. The old %S
+ restartMessageNoUnlockerMac=A copy of %S is already open. Only one copy of %S can be open at a time.
+ restartMessageUnlockerMac=A copy of %S is already open. The running copy of %S will quit in order to open this one.
+
++# LOCALIZATION NOTE (profileProblemTitle, profileReadOnly, profileReadOnlyMac, profileAccessDenied): Messages displayed when the browser profile cannot be accessed or written to. %S is the application name.
++profileProblemTitle=%S Profile Problem
++profileReadOnly=You cannot run %S from a read-only file system. Please copy %S to another location before trying to use it.
++profileReadOnlyMac=You cannot run %S from a read-only file system. Please copy %S to your Desktop or Applications folder before trying to use it.
++profileAccessDenied=%S does not have permission to access the profile. Please adjust your file system permissions and try again.
+ # Profile manager
+ # LOCALIZATION NOTE (profileTooltip): First %S is the profile name, second %S is the path to the profile folder.
+ profileTooltip=Profile: '%S' - Path: '%S'
+diff --git a/toolkit/xre/nsAppRunner.cpp b/toolkit/xre/nsAppRunner.cpp
+index da73cd5..d82f303 100644
+--- a/toolkit/xre/nsAppRunner.cpp
++++ b/toolkit/xre/nsAppRunner.cpp
+@@ -1913,6 +1913,14 @@ static nsresult LaunchChild(nsINativeAppSupport* aNative,
+ return NS_ERROR_LAUNCHED_CHILD_PROCESS;
+ }
+
++enum ProfileStatus {
++ PROFILE_STATUS_OK,
++ PROFILE_STATUS_ACCESS_DENIED,
++ PROFILE_STATUS_READ_ONLY,
++ PROFILE_STATUS_IS_LOCKED,
++ PROFILE_STATUS_OTHER_ERROR
++};
++
+ static const char kProfileProperties[] =
+ "chrome://mozapps/locale/profile/profileSelection.properties";
+
+@@ -1951,9 +1959,9 @@ private:
+ } // namespace
+
+ static ReturnAbortOnError
+-ProfileLockedDialog(nsIFile* aProfileDir, nsIFile* aProfileLocalDir,
+- nsIProfileUnlocker* aUnlocker,
+- nsINativeAppSupport* aNative, nsIProfileLock* *aResult)
++ProfileErrorDialog(nsIFile* aProfileDir, nsIFile* aProfileLocalDir,
++ ProfileStatus aStatus, nsIProfileUnlocker* aUnlocker,
++ nsINativeAppSupport* aNative, nsIProfileLock* *aResult)
+ {
+ nsresult rv;
+
+@@ -1980,18 +1988,31 @@ ProfileLockedDialog(nsIFile* aProfileDir, nsIFile* aProfileLocalDir,
+
+ nsXPIDLString killMessage;
+ #ifndef XP_MACOSX
+- sb->FormatStringFromName(aUnlocker ? MOZ_UTF16("restartMessageUnlocker")
+- : MOZ_UTF16("restartMessageNoUnlocker"),
+- params, 2, getter_Copies(killMessage));
++ static const char16_t kRestartUnlocker[] = MOZ_UTF16("restartMessageUnlocker");
++ static const char16_t kRestartNoUnlocker[] = MOZ_UTF16("restartMessageNoUnlocker");
++ static const char16_t kReadOnly[] = MOZ_UTF16("profileReadOnly");
+ #else
+- sb->FormatStringFromName(aUnlocker ? MOZ_UTF16("restartMessageUnlockerMac")
+- : MOZ_UTF16("restartMessageNoUnlockerMac"),
+- params, 2, getter_Copies(killMessage));
++ static const char16_t kRestartUnlocker[] = MOZ_UTF16("restartMessageUnlockerMac");
++ static const char16_t kRestartNoUnlocker[] = MOZ_UTF16("restartMessageNoUnlockerMac");
++ static const char16_t kReadOnly[] = MOZ_UTF16("profileReadOnlyMac");
+ #endif
++ static const char16_t kAccessDenied[] = MOZ_UTF16("profileAccessDenied");
++
++ const char16_t *errorKey = aUnlocker ? kRestartUnlocker
++ : kRestartNoUnlocker;
++ if (PROFILE_STATUS_READ_ONLY == aStatus)
++ errorKey = kReadOnly;
++ else if (PROFILE_STATUS_ACCESS_DENIED == aStatus)
++ errorKey = kAccessDenied;
++ sb->FormatStringFromName(errorKey, params, 2, getter_Copies(killMessage));
++
++ const char16_t *titleKey = ((PROFILE_STATUS_READ_ONLY == aStatus) ||
++ (PROFILE_STATUS_ACCESS_DENIED == aStatus))
++ ? MOZ_UTF16("profileProblemTitle")
++ : MOZ_UTF16("restartTitle");
+
+ nsXPIDLString killTitle;
+- sb->FormatStringFromName(MOZ_UTF16("restartTitle"),
+- params, 1, getter_Copies(killTitle));
++ sb->FormatStringFromName(titleKey, params, 1, getter_Copies(killTitle));
+
+ if (!killMessage || !killTitle)
+ return NS_ERROR_FAILURE;
+@@ -2092,8 +2113,9 @@ ProfileMissingDialog(nsINativeAppSupport* aNative)
+ }
+
+ static nsresult
+-ProfileLockedDialog(nsIToolkitProfile* aProfile, nsIProfileUnlocker* aUnlocker,
+- nsINativeAppSupport* aNative, nsIProfileLock* *aResult)
++ProfileErrorDialog(nsIToolkitProfile* aProfile, ProfileStatus aStatus,
++ nsIProfileUnlocker* aUnlocker, nsINativeAppSupport* aNative,
++ nsIProfileLock* *aResult)
+ {
+ nsCOMPtr<nsIFile> profileDir;
+ nsresult rv = aProfile->GetRootDir(getter_AddRefs(profileDir));
+@@ -2109,8 +2131,8 @@ ProfileLockedDialog(nsIToolkitProfile* aProfile, nsIProfileUnlocker* aUnlocker,
+ rv = aProfile->GetLocalDir(getter_AddRefs(profileLocalDir));
+ if (NS_FAILED(rv)) return rv;
+
+- return ProfileLockedDialog(profileDir, profileLocalDir, aUnlocker, aNative,
+- aResult);
++ return ProfileErrorDialog(profileDir, profileLocalDir, aStatus, aUnlocker,
++ aNative, aResult);
+ }
+
+ static const char kProfileManagerURL[] =
+@@ -2275,6 +2297,53 @@ SetCurrentProfileAsDefault(nsIToolkitProfileService* aProfileSvc,
+ return rv;
+ }
+
++// Check for write permission to the profile directory by trying to create a
++// new file (after ensuring that no file with the same name exists).
++static ProfileStatus CheckProfileWriteAccess(nsIFile* aProfileDir)
++{
++#if defined(XP_UNIX)
++ NS_NAMED_LITERAL_STRING(writeTestFileName, ".parentwritetest");
++#else
++ NS_NAMED_LITERAL_STRING(writeTestFileName, "parent.writetest");
++#endif
++
++ nsCOMPtr<nsIFile> writeTestFile;
++ nsresult rv = aProfileDir->Clone(getter_AddRefs(writeTestFile));
++ if (NS_SUCCEEDED(rv))
++ rv = writeTestFile->Append(writeTestFileName);
++
++ if (NS_SUCCEEDED(rv)) {
++ bool doesExist = false;
++ rv = writeTestFile->Exists(&doesExist);
++ if (NS_SUCCEEDED(rv) && doesExist)
++ rv = writeTestFile->Remove(true);
++ }
++
++ if (NS_SUCCEEDED(rv)) {
++ rv = writeTestFile->Create(nsIFile::NORMAL_FILE_TYPE, 0666);
++ (void)writeTestFile->Remove(true);
++ }
++
++ ProfileStatus status = NS_SUCCEEDED(rv) ? PROFILE_STATUS_OK
++ : PROFILE_STATUS_OTHER_ERROR;
++ if (NS_ERROR_FILE_ACCESS_DENIED == rv)
++ status = PROFILE_STATUS_ACCESS_DENIED;
++ else if (NS_ERROR_FILE_READ_ONLY == rv)
++ status = PROFILE_STATUS_READ_ONLY;
++
++ return status;
++}
++
++static ProfileStatus CheckProfileWriteAccess(nsIToolkitProfile* aProfile)
++{
++ nsCOMPtr<nsIFile> profileDir;
++ nsresult rv = aProfile->GetRootDir(getter_AddRefs(profileDir));
++ if (NS_FAILED(rv))
++ return PROFILE_STATUS_OTHER_ERROR;
++
++ return CheckProfileWriteAccess(profileDir);
++}
++
+ static bool gDoMigration = false;
+ static bool gDoProfileReset = false;
+
+@@ -2410,13 +2479,18 @@ SelectProfile(nsIProfileLock* *aResult, nsIToolkitProfileService* aProfileSvc, n
+ NS_ENSURE_SUCCESS(rv, rv);
+ }
+
++ ProfileStatus status = CheckProfileWriteAccess(lf);
++ if (PROFILE_STATUS_OK != status)
++ return ProfileErrorDialog(lf, lf, status, nullptr, aNative, aResult);
++
+ // If a profile path is specified directory on the command line, then
+ // assume that the temp directory is the same as the given directory.
+ rv = NS_LockProfilePath(lf, lf, getter_AddRefs(unlocker), aResult);
+ if (NS_SUCCEEDED(rv))
+ return rv;
+
+- return ProfileLockedDialog(lf, lf, unlocker, aNative, aResult);
++ return ProfileErrorDialog(lf, lf, PROFILE_STATUS_IS_LOCKED, unlocker,
++ aNative, aResult);
+ }
+
+ ar = CheckArg("createprofile", true, &arg);
+@@ -2501,6 +2575,10 @@ SelectProfile(nsIProfileLock* *aResult, nsIToolkitProfileService* aProfileSvc, n
+ gDoProfileReset = false;
+ }
+
++ ProfileStatus status = CheckProfileWriteAccess(profile);
++ if (PROFILE_STATUS_OK != status)
++ return ProfileErrorDialog(profile, status, nullptr, aNative, aResult);
++
+ nsCOMPtr<nsIProfileUnlocker> unlocker;
+ rv = profile->Lock(getter_AddRefs(unlocker), aResult);
+ if (NS_SUCCEEDED(rv)) {
+@@ -2509,7 +2587,8 @@ SelectProfile(nsIProfileLock* *aResult, nsIToolkitProfileService* aProfileSvc, n
+ return NS_OK;
+ }
+
+- return ProfileLockedDialog(profile, unlocker, aNative, aResult);
++ return ProfileErrorDialog(profile, PROFILE_STATUS_IS_LOCKED, unlocker,
++ aNative, aResult);
+ }
+
+ if (CanShowProfileManager()) {
+@@ -2589,7 +2668,8 @@ SelectProfile(nsIProfileLock* *aResult, nsIToolkitProfileService* aProfileSvc, n
+ nsCOMPtr<nsIProfileUnlocker> unlocker;
+ rv = profile->Lock(getter_AddRefs(unlocker), &tempProfileLock);
+ if (NS_FAILED(rv))
+- return ProfileLockedDialog(profile, unlocker, aNative, &tempProfileLock);
++ return ProfileErrorDialog(profile, PROFILE_STATUS_IS_LOCKED,
++ unlocker, aNative, &tempProfileLock);
+ }
+
+ nsCOMPtr<nsIToolkitProfile> newProfile;
+@@ -2600,6 +2680,10 @@ SelectProfile(nsIProfileLock* *aResult, nsIToolkitProfileService* aProfileSvc, n
+ gDoProfileReset = false;
+ }
+
++ ProfileStatus status = CheckProfileWriteAccess(profile);
++ if (PROFILE_STATUS_OK != status)
++ return ProfileErrorDialog(profile, status, nullptr, aNative, aResult);
++
+ // If you close Firefox and very quickly reopen it, the old Firefox may
+ // still be closing down. Rather than immediately showing the
+ // "Firefox is running but is not responding" message, we spend a few
+@@ -2625,7 +2709,8 @@ SelectProfile(nsIProfileLock* *aResult, nsIToolkitProfileService* aProfileSvc, n
+ PR_Sleep(kLockRetrySleepMS);
+ } while (TimeStamp::Now() - start < TimeDuration::FromSeconds(kLockRetrySeconds));
+
+- return ProfileLockedDialog(profile, unlocker, aNative, aResult);
++ return ProfileErrorDialog(profile, PROFILE_STATUS_IS_LOCKED, unlocker,
++ aNative, aResult);
+ }
+ }
+
diff --git a/projects/instantbird/Improve-profile-access-bug-14631-second.mozpatch b/projects/instantbird/Improve-profile-access-bug-14631-second.mozpatch
new file mode 100644
index 0000000..3e59cd5
--- /dev/null
+++ b/projects/instantbird/Improve-profile-access-bug-14631-second.mozpatch
@@ -0,0 +1,182 @@
+commit 303992b0684036f6f23d1ca7f76b360930f510db
+Author: Kathy Brade <brade at pearlcrescent.com>
+Date: Fri Feb 27 10:38:40 2015 -0500
+
+ Bug 14631: Improve profile access error msgs (strings).
+
+ To allow for localization, get profile-related error strings from Torbutton.
+ Use app display name ("Tor Browser") in profile-related error alerts.
+
+diff --git a/toolkit/xre/moz.build b/toolkit/xre/moz.build
+index d8127a6..3e6a3b6 100644
+--- a/toolkit/xre/moz.build
++++ b/toolkit/xre/moz.build
+@@ -116,8 +116,8 @@ FINAL_LIBRARY = 'xul'
+ if CONFIG['MOZ_GL_DEFAULT_PROVIDER'] == 'GLX':
+ DEFINES['USE_GLX_TEST'] = True
+
+-for var in ('MOZ_APP_NAME', 'MOZ_APP_BASENAME', 'MOZ_APP_VERSION', 'OS_TARGET',
+- 'MOZ_WIDGET_TOOLKIT'):
++for var in ('MOZ_APP_NAME', 'MOZ_APP_BASENAME', 'MOZ_APP_DISPLAYNAME',
++ 'MOZ_APP_VERSION', 'OS_TARGET', 'MOZ_WIDGET_TOOLKIT'):
+ DEFINES[var] = '"%s"' % CONFIG[var]
+
+ if CONFIG['MOZ_UPDATER'] and CONFIG['MOZ_WIDGET_TOOLKIT'] != 'android':
+diff --git a/toolkit/xre/nsAppRunner.cpp b/toolkit/xre/nsAppRunner.cpp
+index d82f303..a7c7d75 100644
+--- a/toolkit/xre/nsAppRunner.cpp
++++ b/toolkit/xre/nsAppRunner.cpp
+@@ -1913,6 +1913,104 @@ static nsresult LaunchChild(nsINativeAppSupport* aNative,
+ return NS_ERROR_LAUNCHED_CHILD_PROCESS;
+ }
+
++static nsresult
++GetOverrideStringBundleForLocale(nsIStringBundleService* aSBS,
++ const char* aTorbuttonURI, const char* aLocale,
++ nsIStringBundle* *aResult)
++{
++ NS_ENSURE_ARG(aSBS);
++ NS_ENSURE_ARG(aTorbuttonURI);
++ NS_ENSURE_ARG(aLocale);
++ NS_ENSURE_ARG(aResult);
++
++ const char* kFormatStr = "jar:%s!/chrome/locale/%s/torbutton.properties";
++ nsPrintfCString strBundleURL(kFormatStr, aTorbuttonURI, aLocale);
++ nsresult rv = aSBS->CreateBundle(strBundleURL.get(), aResult);
++ NS_ENSURE_SUCCESS(rv, rv);
++
++ // To ensure that we have a valid string bundle, try to retrieve a string
++ // that we know exists.
++ nsXPIDLString val;
++ rv = (*aResult)->GetStringFromName(MOZ_UTF16("profileProblemTitle"),
++ getter_Copies(val));
++ if (!NS_SUCCEEDED(rv))
++ *aResult = nullptr; // No good. Discard it.
++
++ return rv;
++}
++
++static void
++GetOverrideStringBundle(nsIStringBundleService* aSBS, nsIStringBundle* *aResult)
++{
++ if (!aSBS || !aResult)
++ return;
++
++ *aResult = nullptr;
++
++ // Build Torbutton file URI string by starting from the profiles directory.
++ nsXREDirProvider* dirProvider = nsXREDirProvider::GetSingleton();
++ if (!dirProvider)
++ return;
++
++ bool persistent = false; // ignored
++ nsCOMPtr<nsIFile> profilesDir;
++ nsresult rv = dirProvider->GetFile(NS_APP_USER_PROFILES_ROOT_DIR, &persistent,
++ getter_AddRefs(profilesDir));
++ if (NS_FAILED(rv))
++ return;
++
++ // Create file URI, extract as string, and append Torbutton xpi relative path.
++ nsCOMPtr<nsIURI> uri;
++ nsAutoCString uriString;
++ if (NS_FAILED(NS_NewFileURI(getter_AddRefs(uri), profilesDir)) ||
++ NS_FAILED(uri->GetSpec(uriString))) {
++ return;
++ }
++
++ uriString.Append("profile.default/extensions/torbutton at torproject.org.xpi");
++
++ nsCString userAgentLocale;
++ if (!NS_SUCCEEDED(Preferences::GetCString("general.useragent.locale",
++ &userAgentLocale))) {
++ return;
++ }
++
++ rv = GetOverrideStringBundleForLocale(aSBS, uriString.get(),
++ userAgentLocale.get(), aResult);
++ if (NS_FAILED(rv)) {
++ // Try again using base locale, e.g., "en" vs. "en-US".
++ int16_t offset = userAgentLocale.FindChar('-', 1);
++ if (offset > 0) {
++ nsAutoCString shortLocale(Substring(userAgentLocale, 0, offset));
++ rv = GetOverrideStringBundleForLocale(aSBS, uriString.get(),
++ shortLocale.get(), aResult);
++ }
++ }
++}
++
++static nsresult
++GetFormattedString(nsIStringBundle* aOverrideBundle,
++ nsIStringBundle* aMainBundle,
++ const char16_t* aName,
++ const char16_t** aParams, uint32_t aLength,
++ char16_t* *aResult)
++{
++ NS_ENSURE_ARG(aName);
++ NS_ENSURE_ARG(aResult);
++
++ nsresult rv = NS_ERROR_FAILURE;
++ if (aOverrideBundle) {
++ rv = aOverrideBundle->FormatStringFromName(aName, aParams, aLength,
++ aResult);
++ }
++
++ // If string was not found in override bundle, use main (browser) bundle.
++ if (NS_FAILED(rv) && aMainBundle)
++ rv = aMainBundle->FormatStringFromName(aName, aParams, aLength, aResult);
++
++ return rv;
++}
++
+ enum ProfileStatus {
+ PROFILE_STATUS_OK,
+ PROFILE_STATUS_ACCESS_DENIED,
+@@ -1983,7 +2081,10 @@ ProfileErrorDialog(nsIFile* aProfileDir, nsIFile* aProfileLocalDir,
+ sbs->CreateBundle(kProfileProperties, getter_AddRefs(sb));
+ NS_ENSURE_TRUE_LOG(sbs, NS_ERROR_FAILURE);
+
+- NS_ConvertUTF8toUTF16 appName(gAppData->name);
++ nsCOMPtr<nsIStringBundle> overrideSB;
++ GetOverrideStringBundle(sbs, getter_AddRefs(overrideSB));
++
++ NS_ConvertUTF8toUTF16 appName(MOZ_APP_DISPLAYNAME);
+ const char16_t* params[] = {appName.get(), appName.get()};
+
+ nsXPIDLString killMessage;
+@@ -1998,21 +2099,23 @@ ProfileErrorDialog(nsIFile* aProfileDir, nsIFile* aProfileLocalDir,
+ #endif
+ static const char16_t kAccessDenied[] = MOZ_UTF16("profileAccessDenied");
+
+- const char16_t *errorKey = aUnlocker ? kRestartUnlocker
++ const char16_t* errorKey = aUnlocker ? kRestartUnlocker
+ : kRestartNoUnlocker;
+ if (PROFILE_STATUS_READ_ONLY == aStatus)
+ errorKey = kReadOnly;
+ else if (PROFILE_STATUS_ACCESS_DENIED == aStatus)
+ errorKey = kAccessDenied;
+- sb->FormatStringFromName(errorKey, params, 2, getter_Copies(killMessage));
++ GetFormattedString(overrideSB, sb, errorKey, params, 2,
++ getter_Copies(killMessage));
+
+- const char16_t *titleKey = ((PROFILE_STATUS_READ_ONLY == aStatus) ||
++ const char16_t* titleKey = ((PROFILE_STATUS_READ_ONLY == aStatus) ||
+ (PROFILE_STATUS_ACCESS_DENIED == aStatus))
+ ? MOZ_UTF16("profileProblemTitle")
+ : MOZ_UTF16("restartTitle");
+
+ nsXPIDLString killTitle;
+- sb->FormatStringFromName(titleKey, params, 1, getter_Copies(killTitle));
++ GetFormattedString(overrideSB, sb, titleKey, params, 1,
++ getter_Copies(killTitle));
+
+ if (!killMessage || !killTitle)
+ return NS_ERROR_FAILURE;
+@@ -2088,7 +2191,7 @@ ProfileMissingDialog(nsINativeAppSupport* aNative)
+ sbs->CreateBundle(kProfileProperties, getter_AddRefs(sb));
+ NS_ENSURE_TRUE_LOG(sbs, NS_ERROR_FAILURE);
+
+- NS_ConvertUTF8toUTF16 appName(gAppData->name);
++ NS_ConvertUTF8toUTF16 appName(MOZ_APP_DISPLAYNAME);
+ const char16_t* params[] = {appName.get(), appName.get()};
+
+ nsXPIDLString missingMessage;
More information about the tor-commits
mailing list