1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169
|
/*
* Copyright (c) 2006-2007 Los Alamos National Security, LLC. All rights
* reserved.
* Copyright (c) 2007-2010 Cisco Systems, Inc. All rights reserved.
* Copyright (c) 2007 Sun Microsystem, Inc. All rights reserved.
* Copyright (c) 2010 Sandia National Laboratories. All rights reserved.
* Copyright (c) 2018 Amazon.com, Inc. or its affiliates. All Rights reserved.
* $COPYRIGHT$
*
* Additional copyrights may follow
*
* $HEADER$
*
*/
#include "opal_config.h"
#include <string.h>
#include "opal/mca/installdirs/base/base.h"
#include "opal/mca/installdirs/installdirs.h"
#include "opal/util/os_path.h"
#include "opal/util/printf.h"
/* Support both ${name} and @{name} forms. The latter allows us to
pass values through AC_SUBST without being munged by m4 (e.g., if
we want to pass "@{libdir}" and not have it replaced by m4 to be
whatever the actual value of the shell variable is. */
#define EXPAND_STRING(name) EXPAND_STRING2(name, name)
#define EXPAND_STRING2(ompiname, fieldname) \
do { \
if (NULL != (start_pos = strstr(retval, "${" #fieldname "}"))) { \
tmp = retval; \
*start_pos = '\0'; \
end_pos = start_pos + strlen("${" #fieldname "}"); \
opal_asprintf(&retval, "%s%s%s", tmp, opal_install_dirs.ompiname + destdir_offset, \
end_pos); \
free(tmp); \
changed = true; \
} else if (NULL != (start_pos = strstr(retval, "@{" #fieldname "}"))) { \
tmp = retval; \
*start_pos = '\0'; \
end_pos = start_pos + strlen("@{" #fieldname "}"); \
opal_asprintf(&retval, "%s%s%s", tmp, opal_install_dirs.ompiname + destdir_offset, \
end_pos); \
free(tmp); \
changed = true; \
} \
} while (0)
/*
* Read the lengthy comment below to understand the value of the
* is_setup parameter.
*/
static char *opal_install_dirs_expand_internal(const char *input, bool is_setup)
{
size_t len, i;
bool needs_expand = false;
char *retval = NULL;
char *destdir = NULL;
size_t destdir_offset = 0;
/* This is subtle, and worth explaining.
If we substitute in any ${FIELD} values, we need to prepend it
with the value of the $OPAL_DESTDIR environment variable -- if
it is set.
We need to handle at least three cases properly (assume that
configure was invoked with --prefix=/opt/openmpi and no other
directory specifications, and OPAL_DESTDIR is set to
/tmp/buildroot):
1. Individual directories, such as libdir. These need to be
prepended with DESTDIR. I.e., return
/tmp/buildroot/opt/openmpi/lib.
2. Compiler flags that have ${FIELD} values embedded in them.
For example, consider if a wrapper compiler data file
contains the line:
preprocessor_flags=-DMYFLAG="${prefix}/share/randomthingy/"
The value we should return is:
-DMYFLAG="/tmp/buildroot/opt/openmpi/share/randomthingy/"
3. Compiler flags that do not have any ${FIELD} values.
For example, consider if a wrapper compiler data file
contains the line:
preprocessor_flags=-pthread
The value we should return is:
-pthread
Note, too, that this OPAL_DESTDIR futzing only needs to occur
during opal_init(). By the time opal_init() has completed, all
values should be substituted in that need substituting. Hence,
we take an extra parameter (is_setup) to know whether we should
do this futzing or not. */
if (is_setup) {
destdir = getenv("OPAL_DESTDIR");
if (NULL != destdir && strlen(destdir) > 0) {
destdir_offset = strlen(destdir);
}
}
len = strlen(input);
for (i = 0; i < len; ++i) {
if ('$' == input[i] || '@' == input[i]) {
needs_expand = true;
break;
}
}
retval = strdup(input);
if (NULL == retval) {
return NULL;
}
if (needs_expand) {
bool changed = false;
char *start_pos, *end_pos, *tmp;
do {
changed = false;
EXPAND_STRING(prefix);
EXPAND_STRING(exec_prefix);
EXPAND_STRING(bindir);
EXPAND_STRING(sbindir);
EXPAND_STRING(libexecdir);
EXPAND_STRING(datarootdir);
EXPAND_STRING(datadir);
EXPAND_STRING(sysconfdir);
EXPAND_STRING(sharedstatedir);
EXPAND_STRING(localstatedir);
EXPAND_STRING(libdir);
EXPAND_STRING(includedir);
EXPAND_STRING(infodir);
EXPAND_STRING(mandir);
EXPAND_STRING2(opaldatadir, pkgdatadir);
EXPAND_STRING2(opallibdir, pkglibdir);
EXPAND_STRING2(opalincludedir, pkgincludedir);
} while (changed);
}
if (NULL != destdir) {
char *tmp = retval;
retval = opal_os_path(false, destdir, tmp, NULL);
free(tmp);
}
return retval;
}
char *opal_install_dirs_expand(const char *input)
{
/* We do NOT want OPAL_DESTDIR expansion in this case. */
return opal_install_dirs_expand_internal(input, false);
}
char *opal_install_dirs_expand_setup(const char *input)
{
/* We DO want OPAL_DESTDIR expansion in this case. */
return opal_install_dirs_expand_internal(input, true);
}
|