More FIXME cleanup.
--- a/src/physfs.c Fri Mar 23 04:54:20 2012 -0400
+++ b/src/physfs.c Sat Mar 24 00:26:04 2012 -0400
@@ -1102,34 +1102,6 @@
} /* freeDirHandle */
-/*
- * !!! FIXME: remove this and require userdir and basedir to have dirsep
- * !!! FIXME: appended in the platform layer
- */
-static int appendDirSep(char **dir)
-{
- const char dirsep = __PHYSFS_platformDirSeparator;
- char *ptr = *dir;
- const size_t len = strlen(ptr);
-
- if (ptr[len - 1] == dirsep)
- return 1;
-
- ptr = (char *) allocator.Realloc(ptr, len + 2);
- if (!ptr)
- {
- allocator.Free(*dir);
- return 0;
- } /* if */
-
- ptr[len] = dirsep;
- ptr[len+1] = '\0';
-
- *dir = ptr;
- return 1;
-} /* appendDirSep */
-
-
static char *calculateBaseDir(const char *argv0)
{
const char dirsep = __PHYSFS_platformDirSeparator;
@@ -1203,17 +1175,18 @@
baseDir = calculateBaseDir(argv0);
BAIL_IF_MACRO(!baseDir, ERRPASS, 0);
- /* Platform layer is required to append a dirsep. */
- assert(baseDir[strlen(baseDir) - 1] == __PHYSFS_platformDirSeparator);
-
userDir = __PHYSFS_platformCalcUserDir();
- if ((!userDir) || (!appendDirSep(&userDir)))
+ if (!userDir)
{
allocator.Free(baseDir);
baseDir = NULL;
return 0;
} /* if */
+ /* Platform layer is required to append a dirsep. */
+ assert(baseDir[strlen(baseDir) - 1] == __PHYSFS_platformDirSeparator);
+ assert(userDir[strlen(userDir) - 1] == __PHYSFS_platformDirSeparator);
+
initialized = 1;
/* This makes sure that the error subsystem is initialized. */
--- a/src/physfs_internal.h Fri Mar 23 04:54:20 2012 -0400
+++ b/src/physfs_internal.h Sat Mar 24 00:26:04 2012 -0400
@@ -641,8 +641,9 @@
/*
* Get the platform-specific user dir.
- * Caller will allocator.Free() the retval if it's not NULL. If it's NULL,
- * the userdir will default to basedir/username.
+ * As of PhysicsFS 2.1, returning NULL means fatal error.
+ * Your string must end with a dir separator if you don't return NULL.
+ * Caller will allocator.Free() the retval if it's not NULL.
*/
char *__PHYSFS_platformCalcUserDir(void);
@@ -650,12 +651,14 @@
/* This is the cached version from PHYSFS_init(). This is a fast call. */
const char *__PHYSFS_getUserDir(void); /* not deprecated internal version. */
+
/*
- * Get the platform-specific pref dir. You must make sure the string ends
- * with a dir separator.
- * Caller will allocator.Free() the retval if it's not NULL. If it's NULL,
- * it's a total failure. Caller will make missing directories if necessary;
- * this just reports the final path.
+ * Get the platform-specific pref dir.
+ * Returning NULL means fatal error.
+ * Your string must end with a dir separator if you don't return NULL.
+ * Caller will allocator.Free() the retval if it's not NULL.
+ * Caller will make missing directories if necessary; this just reports
+ * the final path.
*/
char *__PHYSFS_platformCalcPrefDir(const char *org, const char *app);
--- a/src/platform_beos.cpp Fri Mar 23 04:54:20 2012 -0400
+++ b/src/platform_beos.cpp Sat Mar 24 00:26:04 2012 -0400
@@ -176,10 +176,12 @@
assert(rc == B_OK);
const char *str = path.Path();
assert(str != NULL);
- char *retval = (char *) allocator.Malloc(strlen(str) + 2);
+ const size_t len = strlen(str);
+ char *retval = (char *) allocator.Malloc(len + 2);
BAIL_IF_MACRO(!retval, PHYSFS_ERR_OUT_OF_MEMORY, NULL);
strcpy(retval, str);
- strcat(retval, "/");
+ retval[len] = '/';
+ retval[len+1] = '\0';
return retval;
} /* __PHYSFS_platformCalcBaseDir */
--- a/src/platform_posix.c Fri Mar 23 04:54:20 2012 -0400
+++ b/src/platform_posix.c Sat Mar 24 00:26:04 2012 -0400
@@ -61,23 +61,6 @@
} /* errcodeFromErrno */
-
-char *__PHYSFS_platformCopyEnvironmentVariable(const char *varname)
-{
- const char *envr = getenv(varname);
- char *retval = NULL;
-
- if (envr != NULL)
- {
- retval = (char *) allocator.Malloc(strlen(envr) + 1);
- BAIL_IF_MACRO(!retval, PHYSFS_ERR_OUT_OF_MEMORY, NULL);
- strcpy(retval, envr);
- } /* if */
-
- return retval;
-} /* __PHYSFS_platformCopyEnvironmentVariable */
-
-
static char *getUserDirByUID(void)
{
uid_t uid = getuid();
@@ -85,11 +68,20 @@
char *retval = NULL;
pw = getpwuid(uid);
- if ((pw != NULL) && (pw->pw_dir != NULL))
+ if ((pw != NULL) && (pw->pw_dir != NULL) && (*pw->pw_dir != '\0'))
{
- retval = (char *) allocator.Malloc(strlen(pw->pw_dir) + 1);
+ const size_t dlen = strlen(pw->pw_dir);
+ const size_t add_dirsep = (pw->pw_dir[dlen-1] != '/') ? 1 : 0;
+ retval = (char *) allocator.Malloc(dlen + 1 + add_dirsep);
if (retval != NULL)
+ {
strcpy(retval, pw->pw_dir);
+ if (add_dirsep)
+ {
+ retval[dlen] = '/';
+ retval[dlen+1] = '\0';
+ } /* if */
+ } /* if */
} /* if */
return retval;
@@ -98,16 +90,27 @@
char *__PHYSFS_platformCalcUserDir(void)
{
- char *retval = __PHYSFS_platformCopyEnvironmentVariable("HOME");
+ char *retval = NULL;
+ char *envr = getenv("HOME");
/* if the environment variable was set, make sure it's really a dir. */
- if (retval != NULL)
+ if (envr != NULL)
{
struct stat statbuf;
- if ((stat(retval, &statbuf) == -1) || (S_ISDIR(statbuf.st_mode) == 0))
+ if ((stat(envr, &statbuf) != -1) && (S_ISDIR(statbuf.st_mode)))
{
- allocator.Free(retval);
- retval = NULL;
+ const size_t envrlen = strlen(envr);
+ const size_t add_dirsep = (envr[envrlen-1] != '/') ? 1 : 0;
+ retval = allocator.Malloc(envrlen + 1 + add_dirsep);
+ if (retval)
+ {
+ strcpy(retval, envr);
+ if (add_dirsep)
+ {
+ retval[envrlen] = '/';
+ retval[envrlen+1] = '\0';
+ } /* if */
+ } /* if */
} /* if */
} /* if */
--- a/src/platform_unix.c Fri Mar 23 04:54:20 2012 -0400
+++ b/src/platform_unix.c Sat Mar 24 00:26:04 2012 -0400
@@ -141,10 +141,6 @@
} /* __PHYSFS_platformDetectAvailableCDs */
-/* this is in posix.c ... */
-extern char *__PHYSFS_platformCopyEnvironmentVariable(const char *varname);
-
-
/*
* See where program (bin) resides in the $PATH specified by (envr).
* returns a copy of the first element in envr that contains it, or NULL
@@ -246,7 +242,7 @@
char *__PHYSFS_platformCalcBaseDir(const char *argv0)
{
char *retval = NULL;
- char *envr = NULL;
+ const char *envr = NULL;
/*
* Try to avoid using argv0 unless forced to. If there's a Linux-like
@@ -269,6 +265,11 @@
char *ptr = strrchr(retval, '/');
if (ptr != NULL)
*(ptr+1) = '\0';
+ else /* shouldn't happen, but just in case... */
+ {
+ allocator.Free(retval);
+ retval = NULL;
+ } /* else */
} /* if */
/* No /proc/self/exe, but we have an argv[0] we can parse? */
@@ -279,11 +280,15 @@
return NULL; /* higher level parses out real path from argv0. */
/* If there's no dirsep on argv0, then look through $PATH for it. */
- /* !!! FIXME: smallAlloc? */
- envr = __PHYSFS_platformCopyEnvironmentVariable("PATH");
- BAIL_IF_MACRO(!envr, ERRPASS, NULL);
- retval = findBinaryInPath(argv0, envr);
- allocator.Free(envr);
+ envr = getenv("PATH");
+ if (envr != NULL)
+ {
+ char *path = (char *) __PHYSFS_smallAlloc(strlen(envr) + 1);
+ BAIL_IF_MACRO(!path, PHYSFS_ERR_OUT_OF_MEMORY, NULL);
+ strcpy(path, envr);
+ retval = findBinaryInPath(argv0, path);
+ __PHYSFS_smallFree(path);
+ } /* if */
} /* if */
if (retval != NULL)