lexer: Use lex_is_string() more consistently.
[pspp] / src / language / lexer / q2c.c
index 3e23390f05a240a31cf06e2e508364fcd89afe28..cf8e53ee5cb881529ead693e0328f66e520a300b 100644 (file)
@@ -1,5 +1,5 @@
 /* PSPP - a program for statistical analysis.
-   Copyright (C) 1997-9, 2000, 2008 Free Software Foundation, Inc.
+   Copyright (C) 1997-9, 2000, 2008, 2010 Free Software Foundation, Inc.
 
    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
@@ -83,8 +83,6 @@ static char *tokstr;
 \f
 /* Utility functions. */
 
-static char nullstr[] = "";
-
 /* Close all open files and delete the output file, on failure. */
 static void
 finish_up (void)
@@ -108,8 +106,8 @@ hcf (void)
   exit (EXIT_FAILURE);
 }
 
-int fail (const char *, ...) PRINTF_FORMAT (1, 2);
-int error (const char *, ...) PRINTF_FORMAT (1, 2);
+int fail (const char *, ...) PRINTF_FORMAT (1, 2) NO_RETURN;
+int error (const char *, ...) PRINTF_FORMAT (1, 2) NO_RETURN;
 
 /* Output an error message and terminate unsuccessfully. */
 int
@@ -227,11 +225,11 @@ st_upper (const char *s)
 /* Returns the address of the first non-whitespace character in S, or
    the address of the null terminator if none. */
 static char *
-skip_ws (const char *s)
+skip_ws (char *s)
 {
   while (isspace ((unsigned char) *s))
     s++;
-  return (char *) s;
+  return s;
 }
 
 /* Read one line from the input file into buf.  Lines having special
@@ -376,10 +374,10 @@ id_cpy (char **cp)
   *dest++ = '\0';
 }
 
-static const char *
+static char *
 unmunge (const char *s)
 {
-  char *dest = xmalloc (strlen (s));
+  char *dest = xmalloc (strlen (s) + 1);
   char *d = dest;
 
   while (*s)
@@ -391,6 +389,7 @@ unmunge (const char *s)
       s++;
       d++;
     }
+  *d = '\0';
 
   return dest;
 }
@@ -973,6 +972,19 @@ dump (int indention, const char *format, ...)
     indent += BASE_INDENT * indention;
 }
 
+/* Writes a blank line to the output file and adjusts 'indent' by BASE_INDENT
+   * INDENTION characters.
+
+   (This is only useful because GCC complains about using "" as a format
+   string, for whatever reason.) */
+static void
+dump_blank_line (int indention)
+{
+  oln++;
+  indent += BASE_INDENT * indention;
+  putc ('\n', out);
+}
+
 /* Write the structure members for specifier SPEC to the output file.
    SBC is the including subcommand. */
 static void
@@ -1068,7 +1080,7 @@ dump_declarations (void)
          if (buf == NULL)
            buf = xmalloc (1024);
          else
-           dump (0, buf);
+           dump (0, "%s", buf);
 
          if (k)
            sprintf (buf, "%s%s,", st_upper (prefix), sym->name);
@@ -1081,13 +1093,13 @@ dump_declarations (void)
     if (buf)
       {
        buf[strlen (buf) - 1] = 0;
-       dump (0, buf);
+       dump (0, "%s", buf);
        free (buf);
       }
     if (f)
       {
        dump (-1, "};");
-       dump (-1, nullstr);
+       dump_blank_line (-1);
       }
   }
 
@@ -1121,7 +1133,7 @@ dump_declarations (void)
            dump (0, "%s%scount", st_upper (prefix), st_upper (sbc->prefix));
 
            dump (-1, "};");
-           dump (-1, nullstr);
+           dump_blank_line (-1);
          }
        }
   }
@@ -1138,7 +1150,7 @@ dump_declarations (void)
        int f = 0;
 
        if (sbc != subcommands)
-         dump (0, nullstr);
+         dump_blank_line (0);
 
        dump (0, "/* %s subcommand. */", sbc->name);
        dump (0, "int sbc_%s;", st_lower (sbc->name));
@@ -1216,7 +1228,7 @@ dump_declarations (void)
       }
 
     dump (-1, "};");
-    dump (-1, nullstr);
+    dump_blank_line (-1);
   }
 
   /* Write out prototypes for custom_*() functions as necessary. */
@@ -1239,7 +1251,7 @@ dump_declarations (void)
        }
 
     if (seen)
-      dump (0, nullstr);
+      dump_blank_line (0);
   }
 
   /* Prototypes for parsing and freeing functions. */
@@ -1249,7 +1261,7 @@ dump_declarations (void)
          make_identifier (cmdname), make_identifier (cmdname));
     dump (0, "static void free_%s (struct cmd_%s *);",
          make_identifier (cmdname), make_identifier (cmdname));
-    dump (0, nullstr);
+    dump_blank_line (0);
   }
 }
 
@@ -1522,7 +1534,7 @@ dump_specifier_parse (const specifier *spec, const subcommand *sbc)
           else if (s->value == VAL_STRING)
             {
               dump (1, "if (lex_token (lexer) != T_ID "
-                    "&& lex_token (lexer) != T_STRING)");
+                    "&& !lex_is_string (lexer))");
               dump (1, "{");
               dump (0, "msg (SE, _(\"%s specifier of %s subcommand "
                     "requires a string argument.\"));",
@@ -1911,13 +1923,13 @@ dump_parser (int persistent)
   dump (0, "break;");
   dump (-2, "}");
   outdent ();
-  dump (0, nullstr);
+  dump_blank_line (0);
   dump (1, "if (lex_token (lexer) != '.')");
   dump (1, "{");
   dump (0, "lex_error (lexer, _(\"expecting end of command\"));");
   dump (0, "goto lossage;");
   dump (-1, "}");
-  dump (0, nullstr);
+  dump_blank_line (0);
 
   outdent ();
 
@@ -1936,19 +1948,19 @@ dump_parser (int persistent)
                  sbc->name);
            dump (0, "goto lossage;");
            dump (-1, "}");
-           dump (0, nullstr);
+           dump_blank_line (0);
          }
       }
   }
 
   dump (-1, "return true;");
-  dump (0, nullstr);
+  dump_blank_line (0);
   dump (-1, "lossage:");
   indent ();
   dump (0, "free_%s (p);", make_identifier (cmdname));
   dump (0, "return false;");
   dump (-1, "}");
-  dump (0, nullstr);
+  dump_blank_line (0);
 }
 
 
@@ -1958,7 +1970,7 @@ dump_header (void)
 {
   indent = 0;
   dump (0,   "/* %s\t\t-*- mode: c; buffer-read-only: t -*-", ofn);
-  dump (0, nullstr);
+  dump_blank_line (0);
   dump (0, "   Generated by q2c from %s.", ifn);
   dump (0, "   Do not modify!");
   dump (0, " */");
@@ -2122,14 +2134,14 @@ main (int argc, char *argv[])
          dump (0, "#include <libpspp/str.h>");
           dump (0, "#include <language/lexer/subcommand-list.h>");
          dump (0, "#include <data/variable.h>");
-         dump (0, nullstr);
+         dump_blank_line (0);
 
           dump (0, "#include \"xalloc.h\"");
-         dump (0, nullstr);
+         dump_blank_line (0);
 
           dump (0, "#include \"gettext.h\"");
           dump (0, "#define _(msgid) gettext (msgid)");
-         dump (0, nullstr);
+         dump_blank_line (0);
        }
       else if (!strcmp (directive, "declarations"))
        dump_declarations ();