Some code cleanups and efficiency enhancements. As far as I can tell
authorPaul Smith <psmith@gnu.org>
Tue, 21 Sep 2004 13:51:58 +0000 (13:51 +0000)
committerPaul Smith <psmith@gnu.org>
Tue, 21 Sep 2004 13:51:58 +0000 (13:51 +0000)
none of these have impacts that are visible to the user (although in
some cases that appears to be nothing more than dumb luck :-/).

ChangeLog
NEWS
read.c
tests/scripts/functions/eval

index b5af21ed78afdcc7611870a28bfebf8d960c7650..4ae898bf8b9cc09d68a3e3f5eaf33804809764f2 100644 (file)
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,10 @@
 2004-09-21  Paul D. Smith  <psmith@gnu.org>
 
+       * read.c (readstring): Fix some logic errors in backslash handling.
+       (eval): Remove some unnecessary processing in buffer handling.
+       (record_target_var): Assert that parse_variable_definition() succeeded.
+       Reported by: Markus Mauhart <qwe123@chello.at>.
+
        * misc.c: Removed the sindex() function.  All instances of this
        function were trivially replaceable by the standard strstr()
        function, and that function will always have better (or certainly
diff --git a/NEWS b/NEWS
index 49f4f57fccb95bcfe761865592ef6493d44a78f1..750bd3bc0cc9183f321ffcf7bb85f0d138bbfc87 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -1,6 +1,6 @@
 GNU make NEWS                                               -*-indented-text-*-
   History of user-visible changes.
-  06 March 2004
+  21 September 2004
 
 Copyright (C) 2002,2003,2004  Free Software Foundation, Inc.
 See the end for copying conditions.
@@ -31,6 +31,11 @@ Version 3.81beta1
   last second and adjust GNU make's view of the system's load average
   accordingly.
 
+* On DOS and MS Windows systems, explicitly setting SHELL to a pathname
+  ending in "cmd" or "cmd.exe" (case-insensitive) will force GNU make to
+  use the DOS command interpreter in batch mode even if a UNIX-like
+  shell could be found on the system.
+
 * Enhancements for POSIX compatibility:
    - Only touch targets (under -t) if they have at least one command.
 
diff --git a/read.c b/read.c
index fc69a8e068b11aacdf57d3e9a05b36480f6a45fa..3704836091d58c14f0abaad78c2cbcdfc0f403d6 100644 (file)
--- a/read.c
+++ b/read.c
@@ -846,21 +846,11 @@ eval (struct ebuffer *ebuf, int set_default)
        /* This line has been dealt with.  */
        goto rule_complete;
 
+      /* This line starts with a tab but was not caught above because there
+         was no preceding target, and the line might have been usable as a
+         variable definition.  But now we know it is definitely lossage.  */
       if (line[0] == '\t')
-       {
-         p = collapsed;        /* Ignore comments, etc.  */
-         while (isblank ((unsigned char)*p))
-           ++p;
-         if (*p == '\0')
-           /* The line is completely blank; that is harmless.  */
-           continue;
-
-         /* This line starts with a tab but was not caught above
-            because there was no preceding target, and the line
-            might have been usable as a variable definition.
-            But now we know it is definitely lossage.  */
-         fatal(fstart, _("commands commence before first target"));
-       }
+        fatal(fstart, _("commands commence before first target"));
 
       /* This line describes some target files.  This is complicated by
          the existence of target-specific variables, because we can't
@@ -1033,13 +1023,11 @@ eval (struct ebuffer *ebuf, int set_default)
            of the unparsed section of p2, for later.  */
         if (*lb_next != '\0')
           {
-            unsigned int l = p - variable_buffer;
-            unsigned int l2 = p2 - variable_buffer;
+            unsigned int l = p2 - variable_buffer;
             plen = strlen (p2);
             (void) variable_buffer_output (p2+plen,
                                            lb_next, strlen (lb_next)+1);
-            p = variable_buffer + l;
-            p2 = variable_buffer + l2;
+            p2 = variable_buffer + l;
           }
 
         /* See if it's an "override" or "export" keyword; if so see if what
@@ -1683,10 +1671,11 @@ record_target_var (struct nameseq *filenames, char *defn,
           /* Get a reference for this pattern-specific variable struct.  */
           p = create_pattern_var (name, percent);
           p->variable.fileinfo = *flocp;
+          /* I don't think this can fail since we already determined it was a
+             variable definition.  */
           v = parse_variable_definition (&p->variable, defn);
+          assert (v != 0);
           v->value = xstrdup (v->value);
-          if (!v)
-            error (flocp, _("Malformed pattern-specific variable definition"));
           fname = p->target;
         }
       else
@@ -2483,35 +2472,42 @@ parse_file_seq (char **stringp, int stopchar, unsigned int size, int strip)
 static unsigned long
 readstring (struct ebuffer *ebuf)
 {
-  char *p;
+  char *eol;
 
   /* If there is nothing left in this buffer, return 0.  */
-  if (ebuf->bufnext > ebuf->bufstart + ebuf->size)
+  if (ebuf->bufnext >= ebuf->bufstart + ebuf->size)
     return -1;
 
   /* Set up a new starting point for the buffer, and find the end of the
      next logical line (taking into account backslash/newline pairs).  */
 
-  p = ebuf->buffer = ebuf->bufnext;
+  eol = ebuf->buffer = ebuf->bufnext;
 
   while (1)
     {
       int backslash = 0;
+      char *bol = eol;
+      char *p;
 
-      /* Find the next newline.  Keep track of backslashes as we look.  */
-      for (; *p != '\n' && *p != '\0'; ++p)
-        if (*p == '\\')
-          backslash = !backslash;
+      /* Find the next newline.  At EOS, stop.  */
+      eol = p = strchr (eol , '\n');
+      if (!eol)
+        {
+          ebuf->bufnext = ebuf->bufstart + ebuf->size + 1;
+          return 0;
+        }
 
-      /* If we got to the end of the string or a newline with no backslash,
-         we're done. */
-      if (*p == '\0' || !backslash)
+      /* Found a newline; if it's escaped continue; else we're done.  */
+      while (p > bol && *(--p) == '\\')
+        backslash = !backslash;
+      if (!backslash)
         break;
+      ++eol;
     }
 
   /* Overwrite the newline char.  */
-  *p = '\0';
-  ebuf->bufnext = p+1;
+  *eol = '\0';
+  ebuf->bufnext = eol+1;
 
   return 0;
 }
index 372aaf8d07b7c69e9eede0847288011ab44a7948..c69a1100792fa2c07aff1a6fc4ace86f25368565 100644 (file)
@@ -134,4 +134,28 @@ $answer = "OK\n";
 
 delete $ENV{EVAR};
 
+
+# Clean out previous information to allow new run_make_test() interface.
+# If we ever convert all the above to run_make_test() we can remove this line.
+$makefile = undef;
+
+# Test handling of backslashes in strings to be evaled.
+
+run_make_test('
+define FOO
+all: ; @echo hello \
+world
+endef
+$(eval $(FOO))
+', '', 'hello world');
+
+run_make_test('
+define FOO
+all: ; @echo he\llo
+       @echo world
+endef
+$(eval $(FOO))
+', '', 'hello
+world');
+
 1;