From a65d5cff5fdc842b9567d56771193820ae48b7b7 Mon Sep 17 00:00:00 2001 From: Dan Nicholson Date: Wed, 17 Apr 2013 07:40:54 -0700 Subject: [PATCH] Allow Windows prefix redefinition in any pkgconfig directory The prefix redefinition feature on Windows to make packages relocatable was being confined only to locations where the .pc file was in a directory ending in lib/pkgconfig or share/pkgconfig. This is too restrictive as it's quite common for the libdir to have a different name such as lib64. This keeps the convention that the feature will only be enabled when the .pc file is in a pkgconfig directory, and it continues to define the prefix to the grandparent of the pkgconfig directory. The path handling is switched over to standard glib functions g_path_get_basename and g_path_get_dirname to avoid handrolled handling of Windows paths. --- parse.c | 51 +++++++++++++++------------------------------------ pkg-config.1 | 19 +++++++++++++------ 2 files changed, 28 insertions(+), 42 deletions(-) diff --git a/parse.c b/parse.c index 4e0857d..6c48e94 100644 --- a/parse.c +++ b/parse.c @@ -857,20 +857,6 @@ parse_url (Package *pkg, const char *str, const char *path) #ifdef G_OS_WIN32 static char *orig_prefix = NULL; - -static int -pathnamecmp (const char *a, - const char *b) -{ - while (*a && *b && - ((G_IS_DIR_SEPARATOR (*a) && G_IS_DIR_SEPARATOR (*b)) || - g_ascii_toupper (*a) == g_ascii_toupper (*b))) - { - a++; - b++; - } - return g_ascii_toupper (*a) - g_ascii_toupper (*b); -} #endif static void @@ -973,31 +959,24 @@ parse_line (Package *pkg, const char *untrimmed, const char *path, /* This is the prefix variable. Try to guesstimate a value for it * for this package from the location of the .pc file. */ + gchar *base; + gboolean is_pkgconfigdir; - gchar *prefix = pkg->pcfiledir; - const int prefix_len = strlen (prefix); - const char *const lib_pkgconfig = "\\lib\\pkgconfig"; - const char *const share_pkgconfig = "\\share\\pkgconfig"; - const int lib_pkgconfig_len = strlen (lib_pkgconfig); - const int share_pkgconfig_len = strlen (share_pkgconfig); - - if ((strlen (prefix) > lib_pkgconfig_len && - pathnamecmp (prefix + prefix_len - lib_pkgconfig_len, lib_pkgconfig) == 0) || - (strlen (prefix) > share_pkgconfig_len && - pathnamecmp (prefix + prefix_len - share_pkgconfig_len, share_pkgconfig) == 0)) - { - /* It ends in lib\pkgconfig or share\pkgconfig. Good. */ + base = g_path_get_basename (pkg->pcfiledir); + is_pkgconfigdir = g_ascii_strcasecmp (base, "pkgconfig") == 0; + g_free (base); + if (is_pkgconfigdir) + { + /* It ends in pkgconfig. Good. */ + gchar *q; + gchar *prefix; - gchar *q; - - orig_prefix = g_strdup (p); + orig_prefix = g_strdup (p); - prefix = g_strdup (prefix); - if (strlen (prefix) > lib_pkgconfig_len && - pathnamecmp (prefix + prefix_len - lib_pkgconfig_len, lib_pkgconfig) == 0) - prefix[prefix_len - lib_pkgconfig_len] = '\0'; - else - prefix[prefix_len - share_pkgconfig_len] = '\0'; + /* Get grandparent directory for new prefix. */ + q = g_path_get_dirname (pkg->pcfiledir); + prefix = g_path_get_dirname (q); + g_free (q); /* Turn backslashes into slashes or * g_shell_parse_argv() will eat them when ${prefix} diff --git a/pkg-config.1 b/pkg-config.1 index 201b473..ce123c9 100644 --- a/pkg-config.1 +++ b/pkg-config.1 @@ -318,15 +318,22 @@ and This can be augmented or replaced using the standard environment variables described above. -If a .pc file is found in a directory that matches the usual -conventions (i.e., ends with \\lib\\pkgconfig or \\share\\pkgconfig), +If a .pc file is found in a directory named +.IR pkgconfig , the prefix for that package is assumed to be the grandparent of the -directory where the file was found, and the \fIprefix\fP variable is -overridden for that file accordingly. +directory where the file was found, and the +.I prefix +variable is overridden for that file accordingly. If the value of a variable in a .pc file begins with the original, -non-overridden, value of the \fIprefix\fP variable, then the overridden -value of \fIprefix\fP is used instead. +non-overridden, value of the +.I prefix +variable, then the overridden value of +.I prefix +is used instead. This allows the feature to work even when the variables +have been expanded in the .pc file. + +See the \-\-dont-define-prefix option for disabling this feature. .\" .SH AUTOCONF MACROS .TP