/* Variable expansion functions for GNU Make.
-Copyright (C) 1988-2020 Free Software Foundation, Inc.
+Copyright (C) 1988-2022 Free Software Foundation, Inc.
This file is part of GNU Make.
GNU Make is free software; you can redistribute it and/or modify it under the
A PARTICULAR PURPOSE. See the GNU General Public License for more details.
You should have received a copy of the GNU General Public License along with
-this program. If not, see <http://www.gnu.org/licenses/>. */
+this program. If not, see <https://www.gnu.org/licenses/>. */
#include "makeint.h"
#include <assert.h>
+#include "commands.h"
+#include "debug.h"
#include "filedef.h"
#include "job.h"
-#include "commands.h"
#include "variable.h"
#include "rule.h"
ptr = variable_buffer + offset;
}
- memcpy (ptr, string, length);
- return ptr + length;
+ return mempcpy (ptr, string, length);
}
-/* Return a pointer to the beginning of the variable buffer. */
+/* Return a pointer to the beginning of the variable buffer.
+ This is called from main() and it should never be null afterward. */
-static char *
-initialize_variable_output (void)
+char *
+initialize_variable_output ()
{
/* If we don't have a variable output buffer yet, get one. */
struct variable_set_list *save = 0;
int set_reading = 0;
+ /* If we're expanding to put into the environment of a shell function then
+ ignore any recursion issues: for backward-compatibility we will use
+ the value of the environment variable we were started with. */
+ if (v->expanding && env_recursion)
+ {
+ size_t nl = strlen (v->name);
+ char **ep;
+ DB (DB_VERBOSE,
+ (_("%s:%lu: not recursively expanding %s to export to shell function\n"),
+ v->fileinfo.filenm, v->fileinfo.lineno, v->name));
+
+ /* We could create a hash for the original environment for speed, but a
+ reasonably written makefile shouldn't hit this situation... */
+ for (ep = environ; *ep != 0; ++ep)
+ if ((*ep)[nl] == '=' && strncmp (*ep, v->name, nl) == 0)
+ return xstrdup ((*ep) + nl + 1);
+
+ /* If there's nothing in the parent environment, use the empty string.
+ This isn't quite correct since the variable should not exist at all,
+ but getting that to work would be involved. */
+ return xstrdup ("");
+ }
+
/* Don't install a new location if this location is empty.
This can happen for command-line variables, builtin variables, etc. */
saved_varp = expanding_var;
if (length == 0)
{
variable_buffer_output (o, "", 1);
- return (variable_buffer);
+ return variable_buffer;
}
/* We need a copy of STRING: due to eval, it's possible that it will get