Commit 7944d248 authored by jeremya@chromium.org's avatar jeremya@chromium.org

[mac] Make app shims look in the correct user data dir on Canary.

On Canary, the user data directory is affected by
[[NSBundle mainBundle] objectForInfoDictionaryKey:@"CrProductDirName"].
Unfortunately in app shims, [NSBundle mainBundle] refers to the app shim's
bundle, not Chrome's bundle. This patch parameterises the
user-data-directory-figuring-out code on the NSBundle, so that app shims can
pass an NSBundle for the real Chrome bundle.

R=thakis@chromium.org


Review URL: https://chromiumcodereview.appspot.com/12663023

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@192644 0039d316-1c4b-4281-b951-d872f2087c98
parent 2f99c553
...@@ -20,6 +20,7 @@ ...@@ -20,6 +20,7 @@
#include "base/strings/sys_string_conversions.h" #include "base/strings/sys_string_conversions.h"
#include "base/threading/thread.h" #include "base/threading/thread.h"
#include "chrome/common/chrome_paths.h" #include "chrome/common/chrome_paths.h"
#include "chrome/common/chrome_paths_internal.h"
#include "chrome/common/chrome_switches.h" #include "chrome/common/chrome_switches.h"
#include "chrome/common/mac/app_mode_common.h" #include "chrome/common/mac/app_mode_common.h"
#include "ipc/ipc_channel_proxy.h" #include "ipc/ipc_channel_proxy.h"
...@@ -68,11 +69,16 @@ AppShimController::AppShimController() : channel_(NULL) { ...@@ -68,11 +69,16 @@ AppShimController::AppShimController() : channel_(NULL) {
void AppShimController::Init() { void AppShimController::Init() {
DCHECK(g_io_thread); DCHECK(g_io_thread);
NSString* chrome_bundle_path =
base::SysUTF8ToNSString(g_info->chrome_outer_bundle_path.value());
NSBundle* chrome_bundle = [NSBundle bundleWithPath:chrome_bundle_path];
base::FilePath user_data_dir; base::FilePath user_data_dir;
if (!PathService::Get(chrome::DIR_USER_DATA, &user_data_dir)) { if (!chrome::GetUserDataDirectoryForBrowserBundle(chrome_bundle,
&user_data_dir)) {
Quit(); Quit();
return; return;
} }
base::FilePath socket_path = base::FilePath socket_path =
user_data_dir.Append(app_mode::kAppShimSocketName); user_data_dir.Append(app_mode::kAppShimSocketName);
IPC::ChannelHandle handle(socket_path.value()); IPC::ChannelHandle handle(socket_path.value());
......
...@@ -92,6 +92,15 @@ bool GetGlobalApplicationSupportDirectory(base::FilePath* result); ...@@ -92,6 +92,15 @@ bool GetGlobalApplicationSupportDirectory(base::FilePath* result);
// inside the helper. In unbundled applications, such as tests, returns nil. // inside the helper. In unbundled applications, such as tests, returns nil.
NSBundle* OuterAppBundle(); NSBundle* OuterAppBundle();
// Get the user data directory for the Chrome browser bundle at |bundle|.
// |bundle| should be the same value that would be returned from +[NSBundle
// mainBundle] if Chrome were launched normaly. This is used by app shims,
// which run from a bundle which isn't Chrome itself, but which need access to
// the user data directory to connect to a UNIX-domain socket therein.
// Returns false if there was a problem fetching the app data directory.
bool GetUserDataDirectoryForBrowserBundle(NSBundle* bundle,
base::FilePath* result);
#endif // OS_MACOSX && !OS_IOS #endif // OS_MACOSX && !OS_IOS
// Checks if the |process_type| has the rights to access the profile. // Checks if the |process_type| has the rights to access the profile.
......
...@@ -13,6 +13,7 @@ ...@@ -13,6 +13,7 @@
#include "base/logging.h" #include "base/logging.h"
#import "base/mac/foundation_util.h" #import "base/mac/foundation_util.h"
#import "base/mac/scoped_nsautorelease_pool.h" #import "base/mac/scoped_nsautorelease_pool.h"
#include "base/memory/scoped_ptr.h"
#include "base/path_service.h" #include "base/path_service.h"
#include "chrome/common/chrome_constants.h" #include "chrome/common/chrome_constants.h"
...@@ -51,24 +52,16 @@ NSBundle* OuterAppBundleInternal() { ...@@ -51,24 +52,16 @@ NSBundle* OuterAppBundleInternal() {
} }
#endif // !defined(OS_IOS) #endif // !defined(OS_IOS)
const char* ProductDirNameInternal() { char* ProductDirNameForBundle(NSBundle* chrome_bundle) {
const char* product_dir_name = NULL; const char* product_dir_name = NULL;
#if !defined(OS_IOS) #if !defined(OS_IOS)
base::mac::ScopedNSAutoreleasePool pool; base::mac::ScopedNSAutoreleasePool pool;
// Use OuterAppBundle() to get the main app's bundle. This key needs to live
// in the main app's bundle because it will be set differently on the canary
// channel, and the autoupdate system dictates that there can be no
// differences between channels within the versioned directory. This would
// normally use base::mac::FrameworkBundle(), but that references the
// framework bundle within the versioned directory. Ordinarily, the profile
// should not be accessed from non-browser processes, but those processes do
// attempt to get the profile directory, so direct them to look in the outer
// browser .app's Info.plist for the CrProductDirName key.
NSBundle* bundle = chrome::OuterAppBundle();
NSString* product_dir_name_ns = NSString* product_dir_name_ns =
[bundle objectForInfoDictionaryKey:@"CrProductDirName"]; [chrome_bundle objectForInfoDictionaryKey:@"CrProductDirName"];
product_dir_name = [product_dir_name_ns fileSystemRepresentation]; product_dir_name = [product_dir_name_ns fileSystemRepresentation];
#else
DCHECK(!chrome_bundle);
#endif #endif
if (!product_dir_name) { if (!product_dir_name) {
...@@ -92,23 +85,42 @@ const char* ProductDirNameInternal() { ...@@ -92,23 +85,42 @@ const char* ProductDirNameInternal() {
// official canary channel, the Info.plist will have CrProductDirName set // official canary channel, the Info.plist will have CrProductDirName set
// to "Google/Chrome Canary". // to "Google/Chrome Canary".
std::string ProductDirName() { std::string ProductDirName() {
static const char* product_dir_name = ProductDirNameInternal(); #if defined(OS_IOS)
static const char* product_dir_name = ProductDirNameForBundle(nil);
#else
// Use OuterAppBundle() to get the main app's bundle. This key needs to live
// in the main app's bundle because it will be set differently on the canary
// channel, and the autoupdate system dictates that there can be no
// differences between channels within the versioned directory. This would
// normally use base::mac::FrameworkBundle(), but that references the
// framework bundle within the versioned directory. Ordinarily, the profile
// should not be accessed from non-browser processes, but those processes do
// attempt to get the profile directory, so direct them to look in the outer
// browser .app's Info.plist for the CrProductDirName key.
static const char* product_dir_name =
ProductDirNameForBundle(chrome::OuterAppBundle());
#endif
return std::string(product_dir_name); return std::string(product_dir_name);
} }
} // namespace bool GetDefaultUserDataDirectoryForProduct(const std::string& product_dir,
base::FilePath* result) {
namespace chrome {
bool GetDefaultUserDataDirectory(base::FilePath* result) {
bool success = false; bool success = false;
if (result && PathService::Get(base::DIR_APP_DATA, result)) { if (result && PathService::Get(base::DIR_APP_DATA, result)) {
*result = result->Append(ProductDirName()); *result = result->Append(product_dir);
success = true; success = true;
} }
return success; return success;
} }
} // namespace
namespace chrome {
bool GetDefaultUserDataDirectory(base::FilePath* result) {
return GetDefaultUserDataDirectoryForProduct(ProductDirName(), result);
}
bool GetUserDocumentsDirectory(base::FilePath* result) { bool GetUserDocumentsDirectory(base::FilePath* result) {
return base::mac::GetUserDirectory(NSDocumentDirectory, result); return base::mac::GetUserDirectory(NSDocumentDirectory, result);
} }
...@@ -218,6 +230,12 @@ NSBundle* OuterAppBundle() { ...@@ -218,6 +230,12 @@ NSBundle* OuterAppBundle() {
return bundle; return bundle;
} }
bool GetUserDataDirectoryForBrowserBundle(NSBundle* bundle,
base::FilePath* result) {
scoped_ptr_malloc<char> product_dir_name(ProductDirNameForBundle(bundle));
return GetDefaultUserDataDirectoryForProduct(product_dir_name.get(), result);
}
#endif // !defined(OS_IOS) #endif // !defined(OS_IOS)
bool ProcessNeedsProfileDir(const std::string& process_type) { bool ProcessNeedsProfileDir(const std::string& process_type) {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment