Alexandre Julliard : libwine: Determine the bin directory independently from the lib directory if possible .
Alexandre Julliard
julliard at winehq.org
Tue Aug 25 08:45:26 CDT 2009
Module: wine
Branch: master
Commit: 995e55371593e4bdcc22aa9e256bb6d42b20f5bf
URL: http://source.winehq.org/git/wine.git/?a=commit;h=995e55371593e4bdcc22aa9e256bb6d42b20f5bf
Author: Alexandre Julliard <julliard at winehq.org>
Date: Tue Aug 25 12:47:50 2009 +0200
libwine: Determine the bin directory independently from the lib directory if possible.
Prefer the bin directory when getting the data dir location.
---
libs/wine/Makefile.in | 1 -
libs/wine/config.c | 155 +++++++++++++++++++++++++++++--------------------
2 files changed, 91 insertions(+), 65 deletions(-)
diff --git a/libs/wine/Makefile.in b/libs/wine/Makefile.in
index 7e7baf1..5af1f94 100644
--- a/libs/wine/Makefile.in
+++ b/libs/wine/Makefile.in
@@ -111,7 +111,6 @@ CONFIGDIRS = \
-DLIB_TO_BINDIR=\"`$(RELPATH) $(libdir) $(bindir)`\" \
-DLIB_TO_DLLDIR=\"`$(RELPATH) $(libdir) $(dlldir)`\" \
-DBIN_TO_DLLDIR=\"`$(RELPATH) $(bindir) $(dlldir)`\" \
- -DLIB_TO_DATADIR=\"`$(RELPATH) $(libdir) $(datadir)/wine`\" \
-DBIN_TO_DATADIR=\"`$(RELPATH) $(bindir) $(datadir)/wine`\"
config.o: config.c $(RELPATH)
diff --git a/libs/wine/config.c b/libs/wine/config.c
index 280241c..6bb87b0 100644
--- a/libs/wine/config.c
+++ b/libs/wine/config.c
@@ -137,6 +137,63 @@ static char *get_runtime_libdir(void)
return NULL;
}
+/* return the directory that contains the main exe at run-time */
+static char *get_runtime_bindir( const char *argv0 )
+{
+ char *p, *bindir, *cwd;
+ size_t len, size;
+
+#ifdef linux
+ for (size = 256; ; size *= 2)
+ {
+ int ret;
+ if (!(bindir = malloc( size ))) break;
+ if ((ret = readlink( "/proc/self/exe", bindir, size )) == -1) break;
+ if (ret != size)
+ {
+ if (!(p = memrchr( bindir, '/', ret ))) break;
+ if (p == bindir) p++;
+ *p = 0;
+ return bindir;
+ }
+ free( bindir );
+ }
+ free( bindir );
+#endif
+
+ if (!(p = strrchr( argv0, '/' ))) return NULL;
+
+ len = p - argv0;
+ if (!len) len++; /* include leading slash */
+
+ if (argv0[0] == '/') /* absolute path */
+ {
+ bindir = xmalloc( len + 1 );
+ memcpy( bindir, argv0, len );
+ bindir[len] = 0;
+ }
+ else
+ {
+ /* relative path, make it absolute */
+ for (size = 256 + len; ; size *= 2)
+ {
+ if (!(cwd = malloc( size ))) return NULL;
+ if (getcwd( cwd, size - len ))
+ {
+ bindir = cwd;
+ cwd += strlen(cwd);
+ *cwd++ = '/';
+ memcpy( cwd, argv0, len );
+ cwd[len] = 0;
+ break;
+ }
+ free( cwd );
+ if (errno != ERANGE) return NULL;
+ }
+ }
+ return bindir;
+}
+
/* initialize the server directory value */
static void init_server_dir( dev_t dev, ino_t ino )
{
@@ -235,6 +292,16 @@ static void init_paths(void)
init_server_dir( st.st_dev, st.st_ino );
}
+/* check if bindir is valid by checking for wineserver */
+static int is_valid_bindir( const char *bindir )
+{
+ struct stat st;
+ char *path = build_path( bindir, "wineserver" );
+ int ret = (stat( path, &st ) != -1);
+ free( path );
+ return ret;
+}
+
/* check if basedir is a valid build dir by checking for wineserver and ntdll */
/* helper for running_from_build_dir */
static inline int is_valid_build_dir( char *basedir, int baselen )
@@ -252,17 +319,10 @@ static inline int is_valid_build_dir( char *basedir, int baselen )
}
/* check if we are running from the build directory */
-static char *running_from_build_dir( const char *basedir, const char *bindir )
+static char *running_from_build_dir( const char *basedir )
{
- struct stat st;
const char *p;
char *path;
- int res;
-
- if (!(path = build_path( bindir, "wineserver" ))) return NULL;
- res = stat( path, &st );
- free( path );
- if (res != -1) return NULL; /* the real bindir is valid */
/* remove last component from basedir */
p = basedir + strlen(basedir) - 1;
@@ -289,73 +349,40 @@ static char *running_from_build_dir( const char *basedir, const char *bindir )
/* initialize the argv0 path */
void wine_init_argv0_path( const char *argv0 )
{
- size_t size, len;
- const char *p, *basename;
- char *cwd, *libdir;
+ const char *basename;
+ char *libdir;
- if (!(p = strrchr( argv0, '/' )))
- basename = argv0;
- else
- basename = p + 1;
+ if (!(basename = strrchr( argv0, '/' ))) basename = argv0;
+ else basename++;
- argv0_name = xstrdup( basename );
+ bindir = get_runtime_bindir( argv0 );
+ libdir = get_runtime_libdir();
- if ((libdir = get_runtime_libdir()))
+ if (bindir && !is_valid_bindir( bindir ))
{
- bindir = build_path( libdir, LIB_TO_BINDIR );
- if ((build_dir = running_from_build_dir( libdir, bindir )))
- {
- free( libdir );
- goto in_build_dir;
- }
- dlldir = build_path( libdir, LIB_TO_DLLDIR );
- datadir = build_path( libdir, LIB_TO_DATADIR );
- free( libdir );
- return;
+ build_dir = running_from_build_dir( bindir );
+ free( bindir );
+ bindir = NULL;
+ }
+ if (libdir && !bindir && !build_dir)
+ {
+ build_dir = running_from_build_dir( libdir );
+ if (!build_dir) bindir = build_path( libdir, LIB_TO_BINDIR );
}
- if (!p) return; /* if argv0 doesn't contain a path, don't store anything */
-
- len = p - argv0;
- if (!len) len++; /* include leading slash */
-
- if (argv0[0] == '/') /* absolute path */
+ if (build_dir)
{
- bindir = xmalloc( len + 1 );
- memcpy( bindir, argv0, len );
- bindir[len] = 0;
+ argv0_name = build_path( "loader/", basename );
}
else
{
- /* relative path, make it absolute */
- for (size = 256 + len; ; size *= 2)
- {
- if (!(cwd = malloc( size ))) return;
- if (getcwd( cwd, size - len ))
- {
- bindir = cwd;
- cwd += strlen(cwd);
- *cwd++ = '/';
- memcpy( cwd, argv0, len );
- cwd[len] = 0;
- break;
- }
- free( cwd );
- if (errno != ERANGE) return;
- }
- }
-
- if ((build_dir = running_from_build_dir( bindir, bindir ))) goto in_build_dir;
-
- dlldir = build_path( bindir, BIN_TO_DLLDIR );
- datadir = build_path( bindir, BIN_TO_DATADIR );
- return;
+ if (libdir) dlldir = build_path( libdir, LIB_TO_DLLDIR );
+ else if (bindir) dlldir = build_path( bindir, BIN_TO_DLLDIR );
-in_build_dir:
- free( bindir );
- free( argv0_name );
- bindir = NULL;
- argv0_name = build_path( "loader/", basename );
+ if (bindir) datadir = build_path( bindir, BIN_TO_DATADIR );
+ argv0_name = xstrdup( basename );
+ }
+ free( libdir );
}
/* return the configuration directory ($WINEPREFIX or $HOME/.wine) */
More information about the wine-cvs
mailing list