summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaul Smith <psmith@gnu.org>2013-11-24 03:45:02 -0500
committerPaul Smith <psmith@gnu.org>2013-11-24 03:45:02 -0500
commitf8905059c3caba75fcbf6481ae6cc2b2eefdd67f (patch)
tree91505684b88bd67572437eaf0181f330cc2a4732
parent12a3104c3d0cbb0e2a0c3e0eed6fe4793d7d2629 (diff)
downloadgunmake-f8905059c3caba75fcbf6481ae6cc2b2eefdd67f.tar.gz
Fix memory leak during environment option decoding.
* main.c (decode_switches): Always make a copy of option arguments. (decode_env_switches): Use a stack buffer to convert environment switches for parsing.
-rw-r--r--main.c21
1 files changed, 11 insertions, 10 deletions
diff --git a/main.c b/main.c
index 6e5d0b3..91b6c2d 100644
--- a/main.c
+++ b/main.c
@@ -2814,7 +2814,7 @@ decode_switches (int argc, char **argv, int env)
if (cs->type == filename)
sl->list[sl->idx++] = expand_command_line_file (optarg);
else
- sl->list[sl->idx++] = optarg;
+ sl->list[sl->idx++] = xstrdup (optarg);
sl->list[sl->idx] = 0;
break;
@@ -2904,7 +2904,7 @@ static void
decode_env_switches (char *envar, unsigned int len)
{
char *varref = alloca (2 + len + 2);
- char *value, *p;
+ char *value, *p, *buf;
int argc;
char **argv;
@@ -2925,15 +2925,18 @@ decode_env_switches (char *envar, unsigned int len)
/* Allocate a vector that is definitely big enough. */
argv = alloca ((1 + len + 1) * sizeof (char *));
- /* Allocate a buffer to copy the value into while we split it into words
- and unquote it. We must use permanent storage for this because
- decode_switches may store pointers into the passed argument words. */
- p = xmalloc (2 * len);
+ /* We need a buffer to copy the value into while we split it into words
+ and unquote it. */
+ buf = alloca (2 * len);
/* getopt will look at the arguments starting at ARGV[1].
Prepend a spacer word. */
argv[0] = 0;
argc = 1;
+
+ /* Set up in case we need to prepend a dash later. */
+ buf[0] = '-';
+ p = buf+1;
argv[argc] = p;
while (*value != '\0')
{
@@ -2956,10 +2959,8 @@ decode_env_switches (char *envar, unsigned int len)
if (argv[1][0] != '-' && strchr (argv[1], '=') == 0)
/* The first word doesn't start with a dash and isn't a variable
- definition. Add a dash and pass it along to decode_switches. We
- need permanent storage for this in case decode_switches saves
- pointers into the value. */
- argv[1] = xstrdup (concat (2, "-", argv[1]));
+ definition, so add a dash. */
+ argv[1] = buf;
/* Parse those words. */
decode_switches (argc, argv, 1);