# HG changeset patch # User rubidium # Date 2007-03-17 11:36:04 # Node ID 48fa3b65b6bbd90120018f5d656f02cc22858087 # Parent 8a67ba84a0d82e184bde0fc6f00cacad7ae38550 (svn r9266) -Codechange: unify the retrieval of the base paths a little more. diff --git a/src/fileio.cpp b/src/fileio.cpp --- a/src/fileio.cpp +++ b/src/fileio.cpp @@ -12,6 +12,7 @@ #include "debug.h" #include "fios.h" #ifndef WIN32 +#include #include #endif @@ -258,24 +259,98 @@ void AppendPathSeparator(char *buf, size } } +#if defined(WIN32) || defined(WINCE) +/** + * Determine the base (personal dir and game data dir) paths + * @param exe the path to the executable + */ +extern void DetermineBasePaths(const char *exe); +#else /* defined(WIN32) || defined(WINCE) */ + +/** + * Changes the working directory to the path of the give executable. + * For OSX application bundles '.app' is the required extension of the bundle, + * so when we crop the path to there, when can remove the name of the bundle + * in the same way we remove the name from the executable name. + * @param exe the path to the executable + */ +void ChangeWorkingDirectory(const char *exe) +{ +#ifdef WITH_COCOA + char *app_bundle = strchr(exe, '.'); + while (app_bundle != NULL && strncasecmp(app_bundle, ".app", 4) != 0) app_bundle = strchr(&app_bundle[1], '.'); + + if (app_bundle != NULL) app_bundle[0] = '\0'; +#endif /* WITH_COCOA */ + char *s = strrchr(exe, PATHSEPCHAR); + if (s != NULL) { + *s = '\0'; + chdir(exe); + *s = PATHSEPCHAR; + } +#ifdef WITH_COCOA + if (app_bundle != NULL) app_bundle[0] = '.'; +#endif /* WITH_COCOA */ +} + /** * Determine the base (personal dir and game data dir) paths - * @note defined in the OS related files (os2.cpp, win32.cpp, unix.cpp etc) + * @param exe the path to the executable */ -extern void DetermineBasePaths(); +void DetermineBasePaths(const char *exe) +{ + /* Change the working directory to enable doubleclicking in UIs */ + ChangeWorkingDirectory(exe); + + _paths.game_data_dir = MallocT(MAX_PATH); + ttd_strlcpy(_paths.game_data_dir, GAME_DATA_DIR, MAX_PATH); +#if defined(SECOND_DATA_DIR) + _paths.second_data_dir = MallocT(MAX_PATH); + ttd_strlcpy(_paths.second_data_dir, SECOND_DATA_DIR, MAX_PATH); +#endif + +#if defined(USE_HOMEDIR) + const char *homedir = getenv("HOME"); + + if (homedir == NULL) { + const struct passwd *pw = getpwuid(getuid()); + if (pw != NULL) homedir = pw->pw_dir; + } + + _paths.personal_dir = str_fmt("%s" PATHSEP "%s", homedir, PERSONAL_DIR); +#else /* not defined(USE_HOMEDIR) */ + _paths.personal_dir = MallocT(MAX_PATH); + ttd_strlcpy(_paths.personal_dir, PERSONAL_DIR, MAX_PATH); + + /* check if absolute or relative path */ + const char *s = strchr(_paths.personal_dir, PATHSEPCHAR); + + /* add absolute path */ + if (s == NULL || _paths.personal_dir != s) { + getcwd(_paths.personal_dir, MAX_PATH); + AppendPathSeparator(_paths.personal_dir, MAX_PATH); + ttd_strlcat(_paths.personal_dir, PERSONAL_DIR, MAX_PATH); + } +#endif /* defined(USE_HOMEDIR) */ + + AppendPathSeparator(_paths.personal_dir, MAX_PATH); + AppendPathSeparator(_paths.game_data_dir, MAX_PATH); +} +#endif /* defined(WIN32) || defined(WINCE) */ /** * Acquire the base paths (personal dir and game data dir), * fill all other paths (save dir, autosave dir etc) and * make the save and scenario directories. + * @param exe the path to the executable * @todo for save_dir, autosave_dir, scenario_dir and heightmap_dir the * assumption is that there is no path separator, however for gm_dir * lang_dir and data_dir that assumption is made. * This inconsistency should be resolved. */ -void DeterminePaths() +void DeterminePaths(const char *exe) { - DetermineBasePaths(); + DetermineBasePaths(exe); _paths.save_dir = str_fmt("%ssave", _paths.personal_dir); _paths.autosave_dir = str_fmt("%s" PATHSEP "autosave", _paths.save_dir); diff --git a/src/fileio.h b/src/fileio.h --- a/src/fileio.h +++ b/src/fileio.h @@ -21,6 +21,6 @@ bool FioCheckFileExists(const char *file void FioCreateDirectory(const char *filename); void AppendPathSeparator(char *buf, size_t buflen); -void DeterminePaths(); +void DeterminePaths(const char *exe); #endif /* FILEIO_H */ diff --git a/src/openttd.cpp b/src/openttd.cpp --- a/src/openttd.cpp +++ b/src/openttd.cpp @@ -433,7 +433,7 @@ int ttd_main(int argc, char *argv[]) } } - DeterminePaths(); + DeterminePaths(argv[0]); CheckExternalFiles(); #if defined(UNIX) && !defined(__MORPHOS__) diff --git a/src/os2.cpp b/src/os2.cpp --- a/src/os2.cpp +++ b/src/os2.cpp @@ -122,18 +122,6 @@ bool FiosIsHiddenFile(const struct diren return ent->d_name[0] == '.'; } - -static void ChangeWorkingDirectory(char *exe) -{ - char *s = strrchr(exe, PATHSEPCHAR); - - if (s != NULL) { - *s = '\0'; - chdir(exe); - *s = PATHSEPCHAR; - } -} - void ShowInfo(const unsigned char *str) { HAB hab; @@ -178,43 +166,6 @@ int CDECL main(int argc, char* argv[]) return ttd_main(argc, argv); } -void DetermineBasePaths() -{ - _paths.game_data_dir = MallocT(MAX_PATH); - ttd_strlcpy(_paths.game_data_dir, GAME_DATA_DIR, MAX_PATH); -#if defined(SECOND_DATA_DIR) - _paths.second_data_dir = MallocT(MAX_PATH); - ttd_strlcpy(_paths.second_data_dir, SECOND_DATA_DIR, MAX_PATH); -#endif - -#if defined(USE_HOMEDIR) - const char *homedir = getenv("HOME"); - - if (homedir == NULL) { - const struct passwd *pw = getpwuid(getuid()); - if (pw != NULL) homedir = pw->pw_dir; - } - - _paths.personal_dir = str_fmt("%s" PATHSEP "%s", homedir, PERSONAL_DIR); -#else /* not defined(USE_HOMEDIR) */ - _paths.personal_dir = MallocT(MAX_PATH); - ttd_strlcpy(_paths.personal_dir, PERSONAL_DIR, MAX_PATH); - - /* check if absolute or relative path */ - const char *s = strchr(_paths.personal_dir, PATHSEPCHAR); - - /* add absolute path */ - if (s == NULL || _paths.personal_dir != s) { - getcwd(_paths.personal_dir, MAX_PATH); - AppendPathSeparator(_paths.personal_dir, MAX_PATH); - ttd_strlcat(_paths.personal_dir, PERSONAL_DIR, MAX_PATH); - } -#endif /* defined(USE_HOMEDIR) */ - - AppendPathSeparator(_paths.personal_dir, MAX_PATH); - AppendPathSeparator(_paths.game_data_dir, MAX_PATH); -} - /** * Insert a chunk of text from the clipboard onto the textbuffer. Get TEXT clipboard * and append this up to the maximum length (either absolute or screenlength). If maxlength diff --git a/src/unix.cpp b/src/unix.cpp --- a/src/unix.cpp +++ b/src/unix.cpp @@ -7,7 +7,6 @@ #include "string.h" #include "table/strings.h" #include "variables.h" -#include "fileio.h" #include #include @@ -101,18 +100,6 @@ bool FiosIsHiddenFile(const struct diren return ent->d_name[0] == '.'; } -#if defined(__BEOS__) || defined(__linux__) -static void ChangeWorkingDirectory(char *exe) -{ - char *s = strrchr(exe, '/'); - if (s != NULL) { - *s = '\0'; - chdir(exe); - *s = '/'; - } -} -#endif - void ShowInfo(const char *str) { fprintf(stderr, "%s\n", str); @@ -131,7 +118,6 @@ void ShowOSErrorBox(const char *buf) } #ifdef WITH_COCOA -void cocoaSetWorkingDirectory(); void cocoaSetupAutoreleasePool(); void cocoaReleaseAutoreleasePool(); #endif @@ -146,15 +132,9 @@ int CDECL main(int argc, char* argv[]) if (argc >= 2 && strncmp(argv[1], "-psn", 4) == 0) { argv[1] = NULL; argc = 1; - cocoaSetWorkingDirectory(); } #endif - // change the working directory to enable doubleclicking in UIs -#if defined(__BEOS__) || defined(__linux__) - ChangeWorkingDirectory(argv[0]); -#endif - _random_seeds[1][1] = _random_seeds[1][0] = _random_seeds[0][1] = _random_seeds[0][0] = time(NULL); SeedMT(_random_seeds[0][1]); @@ -169,43 +149,6 @@ int CDECL main(int argc, char* argv[]) return ret; } -void DetermineBasePaths() -{ - _paths.game_data_dir = MallocT(MAX_PATH); - ttd_strlcpy(_paths.game_data_dir, GAME_DATA_DIR, MAX_PATH); -#if defined(SECOND_DATA_DIR) - _paths.second_data_dir = MallocT(MAX_PATH); - ttd_strlcpy(_paths.second_data_dir, SECOND_DATA_DIR, MAX_PATH); -#endif - -#if defined(USE_HOMEDIR) - const char *homedir = getenv("HOME"); - - if (homedir == NULL) { - const struct passwd *pw = getpwuid(getuid()); - if (pw != NULL) homedir = pw->pw_dir; - } - - _paths.personal_dir = str_fmt("%s" PATHSEP "%s", homedir, PERSONAL_DIR); -#else /* not defined(USE_HOMEDIR) */ - _paths.personal_dir = MallocT(MAX_PATH); - ttd_strlcpy(_paths.personal_dir, PERSONAL_DIR, MAX_PATH); - - /* check if absolute or relative path */ - const char *s = strchr(_paths.personal_dir, PATHSEPCHAR); - - /* add absolute path */ - if (s == NULL || _paths.personal_dir != s) { - getcwd(_paths.personal_dir, MAX_PATH); - AppendPathSeparator(_paths.personal_dir, MAX_PATH); - ttd_strlcat(_paths.personal_dir, PERSONAL_DIR, MAX_PATH); - } -#endif /* defined(USE_HOMEDIR) */ - - AppendPathSeparator(_paths.personal_dir, MAX_PATH); - AppendPathSeparator(_paths.game_data_dir, MAX_PATH); -} - bool InsertTextBufferClipboard(Textbuf *tb) { return false; diff --git a/src/video/cocoa_v.mm b/src/video/cocoa_v.mm --- a/src/video/cocoa_v.mm +++ b/src/video/cocoa_v.mm @@ -2047,22 +2047,6 @@ void CocoaDialog(const char* title, cons _cocoa_video_dialog = false; } - -/* This is needed since OS X applications are started with the working dir set to / when double-clicked */ -void cocoaSetWorkingDirectory() -{ - char parentdir[MAXPATHLEN]; - int chdir_ret; - CFURLRef url = CFBundleCopyBundleURL(CFBundleGetMainBundle()); - CFURLRef url2 = CFURLCreateCopyDeletingLastPathComponent(0, url); - if (CFURLGetFileSystemRepresentation(url2, true, (unsigned char*)parentdir, MAXPATHLEN)) { - chdir_ret = chdir(parentdir); /* chdir to the binary app's parent */ - assert(chdir_ret == 0); - } - CFRelease(url); - CFRelease(url2); -} - /* These are called from main() to prevent a _NSAutoreleaseNoPool error when * exiting before the cocoa video driver has been loaded */ diff --git a/src/win32.cpp b/src/win32.cpp --- a/src/win32.cpp +++ b/src/win32.cpp @@ -943,7 +943,7 @@ void GetCurrentDirectoryW(int length, wc } #endif -void DetermineBasePaths() +void DetermineBasePaths(const char *exe) { _paths.personal_dir = _paths.game_data_dir = MallocT(MAX_PATH); #if defined(UNICODE)