[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[GNUnet-SVN] r3283 - in GNUnet/src: include setup util/os
From: |
grothoff |
Subject: |
[GNUnet-SVN] r3283 - in GNUnet/src: include setup util/os |
Date: |
Sun, 20 Aug 2006 21:29:19 -0700 (PDT) |
Author: grothoff
Date: 2006-08-20 21:29:15 -0700 (Sun, 20 Aug 2006)
New Revision: 3283
Modified:
GNUnet/src/include/gnunet_util_os.h
GNUnet/src/setup/gnunet-setup.c
GNUnet/src/util/os/dso.c
GNUnet/src/util/os/installpath.c
Log:
cleaning up installpath (memory leak, cannot use cfg/ectx during startup, use
in dso, code cleanup)
Modified: GNUnet/src/include/gnunet_util_os.h
===================================================================
--- GNUnet/src/include/gnunet_util_os.h 2006-08-21 02:15:09 UTC (rev 3282)
+++ GNUnet/src/include/gnunet_util_os.h 2006-08-21 04:29:15 UTC (rev 3283)
@@ -269,12 +269,12 @@
* List of install paths
*/
enum InstallPathKind {
- PREFIX,
- BINDIR,
- LIBDIR,
- GNDATADIR,
- PACKAGEDATADIR,
- LOCALEDIR };
+ IPK_PREFIX,
+ IPK_BINDIR,
+ IPK_LIBDIR,
+ IPK_DATADIR,
+ IPK_LOCALEDIR
+};
/**
* @brief get the path to a specific app dir
@@ -283,9 +283,7 @@
* @param cfg the context to get configuration values from
* @return a pointer to the dir path (to be freed by the caller)
*/
-char * os_get_installation_path(struct GE_Context * ectx,
- struct GC_Configuration * cfg,
- enum InstallPathKind dirkind);
+char * os_get_installation_path(enum InstallPathKind dirkind);
Modified: GNUnet/src/setup/gnunet-setup.c
===================================================================
--- GNUnet/src/setup/gnunet-setup.c 2006-08-21 02:15:09 UTC (rev 3282)
+++ GNUnet/src/setup/gnunet-setup.c 2006-08-21 04:29:15 UTC (rev 3283)
@@ -200,16 +200,14 @@
if(0 == ACCESS(filename, F_OK))
GC_parse_configuration(cfg,
filename);
- dirname = os_get_installation_path(ectx,
- cfg,
- GNDATADIR);
- specname = MALLOC(strlen(dirname) + strlen("/config-daemon.scm") + 1);
+ dirname = os_get_installation_path(IPK_DATADIR);
+ specname = MALLOC(strlen(dirname) + strlen("config-daemon.scm") + 1);
strcpy(specname, dirname);
FREE(dirname);
if (config_daemon)
- strcat(specname, "/config-daemon.scm");
+ strcat(specname, "config-daemon.scm");
else
- strcat(specname, "/config-client.scm");
+ strcat(specname, "config-client.scm");
gns = GNS_load_specification(ectx,
cfg,
specname);
Modified: GNUnet/src/util/os/dso.c
===================================================================
--- GNUnet/src/util/os/dso.c 2006-08-21 02:15:09 UTC (rev 3282)
+++ GNUnet/src/util/os/dso.c 2006-08-21 04:29:15 UTC (rev 3283)
@@ -38,68 +38,7 @@
static char * old_dlsearchpath;
-static char * getPluginPath() {
-#if LINUX
- char * fn;
- char * lnk;
- size_t size;
- fn = MALLOC(64);
- SNPRINTF(fn,
- 64,
- "/proc/%u/exe",
- getpid());
- lnk = MALLOC(1024);
- size = readlink(fn, lnk, 1023);
- if ( (size == 0) || (size >= 1024) ) {
- GE_LOG_STRERROR_FILE(NULL,
- GE_ERROR | GE_USER | GE_ADMIN | GE_IMMEDIATE,
- "readlink",
- fn);
- FREE(fn);
- FREE(lnk);
- return NULL;
- }
- FREE(fn);
- lnk[size] = '\0';
- while ( (lnk[size] != '/') &&
- (size > 0) )
- size--;
- if ( (size < 4) ||
- (lnk[size-4] != '/') ) {
- GE_LOG(NULL,
- GE_ERROR | GE_USER | GE_ADMIN | GE_IMMEDIATE,
- _("Cannot determine plugin path (have, application must be installed
in directory ending with `%s', have `%s').\n"),
- "bin/",
- lnk);
- FREE(lnk);
- return NULL;
- }
- lnk[ size] = '\0';
- lnk[--size] = 'b';
- lnk[--size] = 'i';
- lnk[--size] = 'l';
- return lnk;
-#elif WINDOWS
- char *path, *idx;
-
- path = MALLOC(4097);
- GetModuleFileName(NULL, path, 4096);
- idx = path + strlen(idx);
- while ( (idx > path) &&
- (path != '\\') &&
- (path != '/') )
- idx++;
- *idx = 0;
-
- return path;
-#else
-/* FIXME/PORTME to other platforms */
-#error Missing port: getPluginPath()
- Missing port: getPluginPath();
-#endif
-}
-
/* using libtool, needs init! */
void __attribute__ ((constructor)) gnc_ltdl_init(void) {
int err;
@@ -116,14 +55,11 @@
opath = lt_dlgetsearchpath();
if (opath != NULL)
old_dlsearchpath = STRDUP(opath);
- path = getPluginPath();
- if (path == NULL) {
- fprintf(stderr,
- _("Fatal error: could not determine path for plugins!\n"));
- abort();
+ path = os_get_installation_path(IPK_LIBDIR);
+ if (path != NULL) {
+ lt_dlsetsearchpath(path);
+ FREE(path);
}
- lt_dlsetsearchpath(path);
- FREE(path);
}
void __attribute__ ((destructor)) gnc_ltdl_fini(void) {
@@ -132,7 +68,7 @@
FREE(old_dlsearchpath);
old_dlsearchpath = NULL;
}
- lt_dlexit ();
+ lt_dlexit();
}
struct PluginHandle *
Modified: GNUnet/src/util/os/installpath.c
===================================================================
--- GNUnet/src/util/os/installpath.c 2006-08-21 02:15:09 UTC (rev 3282)
+++ GNUnet/src/util/os/installpath.c 2006-08-21 04:29:15 UTC (rev 3283)
@@ -39,226 +39,209 @@
#include "platform.h"
#include "gnunet_util_string.h"
#include "gnunet_util_config.h"
+#include "gnunet_util_disk.h"
#include "gnunet_util_os.h"
-/* assumed math size for a path
- * used to try allocating less memory than PATH_MAX */
-#define PATH_TRY 96
-
-
-/*
- * @brief get the path to the executable, including the binary itself
- * @author Milan
- * @param ectx the context to report the errors to
- * @param cfg the context to get configuration values from
- * @return a pointer to the executable path, owned by the function (don't free
it)
+#if LINUX
+/**
+ * Try to determine path by reading /proc/PID/exe
*/
-static char *os_get_exec_path(struct GE_Context * ectx,
- struct GC_Configuration * cfg) {
- static char *execpath = NULL; /* save it between calls */
- int found;
+static char *
+get_path_from_proc_exe() {
+ char * fn;
+ char * lnk;
+ size_t size;
-#ifdef WINDOWS
-/* FIXME MINGW: get the path
- * set found and execpath so the end of the function is valid */
-
- found = 0;
-#else /* Should work on all Unices, else we won't run */
- /* FIXME: we assume PATH_MAX is the same for all used files */
- const long path_max = pathconf(".", _PC_PATH_MAX);
- const long name_max = pathconf(".", _PC_NAME_MAX);
-
- char *tmp, *path1, *path2, *path3;
- size_t size, size1, size2;
- struct stat dummy_stat;
-
- if(execpath) /* already got the path, don't work more */
- return execpath;
-
- /* I. get the path from /proc */
- tmp = MALLOC(name_max+10);
- SNPRINTF(tmp,
- name_max+10,
+ fn = MALLOC(64);
+ SNPRINTF(fn,
+ 64,
"/proc/%u/exe",
getpid());
- path1 = MALLOC(PATH_TRY); /* let's try with a little buffer */
- size = readlink(tmp, path1, PATH_TRY-1);
- if(size == PATH_TRY) { /* buffer too small */
- path1 = REALLOC(path1, path_max);
- size = readlink(tmp, path1, path_max-1); }
- FREE(tmp);
- if (size > 0) { /* this method worked well */
- path1[size] = '\0';
+ lnk = MALLOC(1024);
+ size = readlink(fn, lnk, 1023);
+ if ( (size == 0) || (size >= 1024) ) {
+ GE_LOG_STRERROR_FILE(NULL,
+ GE_ERROR | GE_USER | GE_ADMIN | GE_IMMEDIATE,
+ "readlink",
+ fn);
+ FREE(fn);
+ FREE(lnk);
+ return NULL;
+ }
+ FREE(fn);
+ lnk[size] = '\0';
+ while ( (lnk[size] != '/') &&
+ (size > 0) )
+ size--;
+ if ( (size < 4) ||
+ (lnk[size-4] != '/') ) {
+ /* not installed in "/bin/" -- binary path probably useless */
+ FREE(lnk);
+ return NULL;
+ }
+ lnk[size] = '\0';
+ return lnk;
+}
+#endif
- execpath = STRDUP(path1);
- FREE(path1);
- return execpath; }
+#if WINDOWS
+/**
+ * Try to determine path with win32-specific function
+ */
+char * get_path_from_module_filename() {
+ char * path;
+ char * idx;
+
+ path = MALLOC(4097);
+ GetModuleFileName(NULL, path, 4096);
+ idx = path + strlen(idx);
+ while ( (idx > path) &&
+ (path != '\\') &&
+ (path != '/') )
+ idx++;
+ *idx = '\0';
+ return path;
+}
+#endif
- FREE(path1);
+static char *
+get_path_from_PATH() {
+ char * path;
+ char * pos;
+ char * end;
+ char * buf;
+ const char * p;
+ size_t size;
+ p = getenv("PATH");
+ if (p == NULL)
+ return NULL;
+ path = STRDUP(p); /* because we write on it */
+ buf = MALLOC(strlen(path) + 20);
+ size = strlen(path);
+ pos = path;
- /* II. reading /proc failed, trying with argv[0] */
- found = 0;
- GC_get_configuration_value_string(cfg,
- "ARGV",
- "0",
- "gnunetd",
- &path1);
-
- /* 1. absolute path */
- if (*path1 == '/') {
- execpath = path1;
- found = 1; }
-
- /* 2. relative path */
- else if(strchr(path1, '/')) {
- tmp = MALLOC(PATH_TRY); /* let's try with a little buffer */
- if( !getcwd(tmp, PATH_TRY-1) ) { /* buffer too small */
- tmp = REALLOC(tmp, path_max);
- getcwd(tmp, path_max-1); }
-
- if( (*path1 == '.') && (*(path1+1) == '.') ) { /* ../ so go one level
higher */
- strchr(tmp, '/')[0] = '\0';
- path2 = path1+3;
- } /* and jump */
- else if (*path1 == '.') /* ./ so just jump */
- path2 = path1+2;
- else
- path2 = path1;
-
- if(tmp[strlen(tmp)-1] == '/') /* just to clean final '/' */
- tmp[strlen(tmp)-1] = '\0';
-
- execpath = MALLOC(strlen(tmp)+strlen(path1)+2);
- sprintf(execpath, "%s/%s", tmp, path1);
- FREE(tmp);
- FREE(path1);
- found = 1; }
-
- /* 3. program in PATH */
- else {
- path3 = MALLOC(PATH_TRY);
- tmp = STRDUP(getenv("PATH")); /* because we write on it */
- size = strlen(path1);
- size1 = PATH_TRY;
-
- while(strchr(tmp, ':')) {
- path2 = (strrchr(tmp, ':')+1);
- size2 = strlen(path2)+size+2;
- if(size2 > size1) {
- path3 = REALLOC(path3, size2); /* not nice, but best to do: */
- size1 = size2; } /* malloc PATH_MAX bytes is too much */
-
- sprintf(path3, "%s/%s", path2, path1);
- if(stat(path3, &dummy_stat) == 0) {
- found = 1;
- break; }
- *(path2-1) = '\0';
+ while (NULL != (end = strchr(pos, ':'))) {
+ *end = '\0';
+ sprintf(buf, "%s/%s", pos, "gnunetd");
+ if (disk_file_test(NULL, buf) == YES) {
+ pos = STRDUP(pos);
+ FREE(buf);
+ FREE(path);
+ return pos;
}
+ pos = end + 1;
+ }
+ sprintf(buf, "%s/%s", pos, "gnunetd");
+ if (disk_file_test(NULL, buf) == YES) {
+ pos = STRDUP(pos);
+ FREE(buf);
+ FREE(path);
+ return pos;
+ }
+ FREE(buf);
+ FREE(path);
+ return NULL;
+}
- if(!found) { /* first dir in PATH */
- path2 = tmp;
- sprintf(path3, "%s/%s", path2, path1);
- if(STAT(path3, &dummy_stat) == 0)
- found = 1; }
+static char *
+get_path_from_GNUNET_PREFIX() {
+ const char * p;
- execpath = STRDUP(path3);
+ p = getenv("GNUNET_PREFIX");
+ if (p != NULL)
+ return STRDUP(p);
+ return NULL;
+}
- FREE(path1);
- FREE(path3);
- FREE(tmp); }
+/*
+ * @brief get the path to the executable, including the binary itself
+ * @author Milan
+ *
+ * @return a pointer to the executable path, or NULL on error
+ */
+static char *
+os_get_exec_path() {
+ char * ret;
+ ret = get_path_from_GNUNET_PREFIX();
+ if (ret != NULL)
+ return ret;
+#if LINUX
+ ret = get_path_from_proc_exe();
+ if (ret != NULL)
+ return ret;
#endif
- if(found) {
- return execpath; }
- else { /* we can do nothing to run normally */
- GE_LOG(ectx, /* This error should not occur on standard Unices */
- GE_ERROR | GE_USER | GE_ADMIN | GE_DEVELOPER | GE_IMMEDIATE,
- _("Cannot determine the path to the executable, your system may be
broken or not supported.\n"));
- return NULL; }
+#if WINDOWS
+ ret = get_path_from_module_filename();
+ if (ret != NULL)
+ return ret;
+#endif
+ ret = get_path_from_PATH();
+ if (ret != NULL)
+ return ret;
+ /* other attempts here */
+ return NULL;
}
+
+
/*
* @brief get the path to a specific app dir
* @author Milan
- * @param ectx the context to report the errors to
- * @param cfg the context to get configuration values from
* @return a pointer to the dir path (to be freed by the caller)
*/
-char * os_get_installation_path(struct GE_Context * ectx,
- struct GC_Configuration * cfg,
- enum InstallPathKind dirkind) {
-
- static char *prefix = NULL; /*save it between calls */
-
- unsigned int n;
+char * os_get_installation_path(enum InstallPathKind dirkind) {
+ size_t n;
const char * dirname;
- char *execpath;
- char *tmp;
- char *ptr;
+ char * execpath;
+ char * tmp;
- if(!prefix) { /* if we already got the prefix once, don't work more */
- if( !(execpath = os_get_exec_path(ectx, cfg)) )
- return NULL;
+ execpath = os_get_exec_path();
+ if (execpath == NULL)
+ return NULL;
- tmp = STRDUP(execpath);
- ptr = strrchr(tmp, DIR_SEPARATOR); /* get prefix from prefix/bin/app */
- *ptr = '\0';
- n = 1;
- while( *(ptr-n) == DIR_SEPARATOR ) { /* manage "//" in the path */
- *(ptr-n) = '\0';
- n++; }
- ptr = strrchr(tmp, DIR_SEPARATOR);
-
- if( !( (*(ptr+1) == 'b')
- && (*(ptr+2) == 'i')
- && (*(ptr+3) == 'n')) )
- GE_LOG(ectx,
- GE_WARNING | GE_ADMIN | GE_IMMEDIATE,
- _("GNUnet executables are not in a directory named 'bin'. This
may signal a broken installation.\n"));
-
- *(ptr+1) = '\0';
- n = 1;
- while( *(ptr-n) == DIR_SEPARATOR ) { /* same, but keep the final '/' */
- *(ptr-n+1) = '\0';
- n++; }
-
- if(*tmp == '\0') { /* no prefix at all */
- GE_LOG(ectx,
- GE_ERROR | GE_USER | GE_ADMIN | GE_DEVELOPER | GE_IMMEDIATE,
- _("Cannot determine the installation prefix. Unknown error.\n"));
- return NULL; }
-
- prefix = STRDUP(tmp);
- FREE(tmp); }
-
-
+ n = strlen(execpath);
+ if (n == 0) {
+ /* should never happen, but better safe than sorry */
+ FREE(execpath);
+ return NULL;
+ }
+ if (execpath[n-1] == DIR_SEPARATOR)
+ execpath[--n] = '\0';
+
+ if ( (n > 3) &&
+ (0 == strcmp(&execpath[n-3], "bin")) ) {
+ /* good, strip of '/bin'! */
+ execpath[n-3] = '\0';
+ n -= 3;
+ }
switch(dirkind) {
- case PREFIX:
- dirname = "";
- break;
- case BINDIR:
- dirname = "bin/";
- break;
- case LIBDIR:
- dirname = "lib/GNUnet/";
- break;
- case PACKAGEDATADIR:
- case GNDATADIR:
- dirname = "share/GNUnet/";
- break;
- case LOCALEDIR:
- dirname = "share/locale/";
- break;
- default:
- return NULL; }
-
- tmp = MALLOC(strlen(prefix)+strlen(dirname)+1);
+ case IPK_PREFIX:
+ dirname = "";
+ break;
+ case IPK_BINDIR:
+ dirname = "bin/";
+ break;
+ case IPK_LIBDIR:
+ dirname = "lib/GNUnet/";
+ break;
+ case IPK_DATADIR:
+ dirname = "share/GNUnet/";
+ break;
+ case IPK_LOCALEDIR:
+ dirname = "share/locale/";
+ break;
+ default:
+ FREE(execpath);
+ return NULL;
+ }
+ tmp = MALLOC(strlen(execpath)+strlen(dirname)+1);
sprintf(tmp,
"%s%s",
- prefix,
+ execpath,
dirname);
- FREE(prefix);
+ FREE(execpath);
return tmp;
}
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [GNUnet-SVN] r3283 - in GNUnet/src: include setup util/os,
grothoff <=