Adopt use of gnulib for portability.
[pspp-builds.git] / src / repeat.c
index aef5e9842db1679c8ecee195e0ce9ccc85b67b4c..0f5bb42f4dbc4aec79b75417b040f4c779314a57 100644 (file)
 
    You should have received a copy of the GNU General Public License
    along with this program; if not, write to the Free Software
-   Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
-   02111-1307, USA. */
+   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+   02110-1301, USA. */
 
 #include <config.h>
-#include <assert.h>
+#include "repeat.h"
+#include "error.h"
 #include <ctype.h>
 #include <math.h>
 #include <stdlib.h>
 #include "alloc.h"
-#include "cases.h"
 #include "command.h"
+#include "dictionary.h"
 #include "error.h"
-#include "getline.h"
+#include "getl.h"
 #include "lexer.h"
 #include "misc.h"
 #include "settings.h"
 #include "str.h"
 #include "var.h"
 
+#include "gettext.h"
+#define _(msgid) gettext (msgid)
+
 #include "debug-print.h"
 
 /* Describes one DO REPEAT macro. */
 struct repeat_entry
   {
     int type;                  /* 1=variable names, 0=any other. */
-    char id[9];                        /* Macro identifier. */
+    char id[LONG_NAME_LEN + 1];        /* Macro identifier. */
     char **replacement;                /* Macro replacement. */
     struct repeat_entry *next;
   };
@@ -60,11 +64,6 @@ static int parse_strings (struct repeat_entry *);
 static void clean_up (void);
 static int internal_cmd_do_repeat (void);
 
-#if DEBUGGING
-static void debug_print (void);
-static void debug_print_lines (void);
-#endif
-
 int
 cmd_do_repeat (void)
 {
@@ -129,7 +128,7 @@ static int
 internal_cmd_do_repeat (void)
 {
   /* Name of first DO REPEAT macro. */
-  char first_name[9];
+  char first_name[LONG_NAME_LEN + 1];
 
   /* Current filename. */
   const char *current_filename = NULL;
@@ -138,9 +137,6 @@ internal_cmd_do_repeat (void)
   int print;
 
   /* The first step is parsing the DO REPEAT command itself. */
-  lex_match_id ("DO");
-  lex_match_id ("REPEAT");
-
   count = 0;
   line_buf_head = NULL;
   do
@@ -153,7 +149,7 @@ internal_cmd_do_repeat (void)
       if (!lex_force_id ())
        return 0;
       for (iter = repeat_tab; iter; iter = iter->next)
-       if (!strcmp (iter->id, tokid))
+       if (!strcasecmp (iter->id, tokid))
          {
            msg (SE, _("Identifier %s is given twice."), tokid);
            return 0;
@@ -176,7 +172,7 @@ internal_cmd_do_repeat (void)
       
       if (token == T_ID)
        result = parse_ids (e);
-      else if (token == T_NUM)
+      else if (lex_is_number ())
        result = parse_numbers (e);
       else if (token == T_STRING)
        result = parse_strings (e);
@@ -211,10 +207,6 @@ internal_cmd_do_repeat (void)
     }
   while (token != '.');
 
-#if DEBUGGING
-  debug_print ();
-#endif
-
   /* Read all the lines inside the DO REPEAT ... END REPEAT. */
   {
     int nest = 1;
@@ -248,7 +240,7 @@ internal_cmd_do_repeat (void)
           command names must appear on a single line--they can't be
           spread out. */
        {
-         char *cp = ds_value (&getl_buf);
+         char *cp = ds_c_str (&getl_buf);
 
          /* Skip leading indentors and any whitespace. */
          if (*cp == '+' || *cp == '-' || *cp == '.')
@@ -294,7 +286,7 @@ internal_cmd_do_repeat (void)
        line_buf_tail->len = ds_length (&getl_buf);
        line_buf_tail->line = xmalloc (ds_length (&getl_buf) + 1);
        memcpy (line_buf_tail->line,
-               ds_value (&getl_buf), ds_length (&getl_buf) + 1);
+               ds_c_str (&getl_buf), ds_length (&getl_buf) + 1);
       }
   }
 
@@ -302,7 +294,7 @@ internal_cmd_do_repeat (void)
      REPEAT line.  We should actually check for the PRINT specifier.
      This can be done easier when we buffer entire commands instead of
      doing it token by token; see TODO. */
-  lex_entire_line ();  
+  lex_discard_line (); 
   
   /* Tie up the loose end of the chain. */
   if (line_buf_head == NULL)
@@ -312,11 +304,6 @@ internal_cmd_do_repeat (void)
     }
   line_buf_tail->next = NULL;
 
-  /* Show the line list. */
-#if DEBUGGING
-  debug_print_lines ();
-#endif
-  
   /* Make new variables. */
   {
     struct repeat_entry *iter;
@@ -328,14 +315,7 @@ internal_cmd_do_repeat (void)
            {
              /* Note that if the variable already exists there is no
                 harm done. */
-             struct variable *v = create_variable (&default_dict,
-                                                   iter->replacement[i],
-                                                   NUMERIC, 0);
-
-             /* If we created the variable then we need to initialize
-                its observations to SYSMIS. */
-             if (v)
-               envector (v);
+             dict_create_var (default_dict, iter->replacement[i], 0);
            }
        }
   }
@@ -513,7 +493,7 @@ cmd_end_repeat (void)
 \f
 /* Finds a DO REPEAT macro with name MACRO_NAME and returns the
    appropriate subsitution if found, or NULL if not. */
-char *
+static char *
 find_DO_REPEAT_substitution (char *macro_name)
 {
   struct getl_script *s;
@@ -549,19 +529,19 @@ perform_DO_REPEAT_substitutions (void)
   /* Terminal dot. */
   int dot = 0;
 
-  ds_init (NULL, &output, ds_size (&getl_buf));
+  ds_init (&output, ds_capacity (&getl_buf));
 
   /* Strip trailing whitespace, check for & remove terminal dot. */
   while (ds_length (&getl_buf) > 0
         && isspace ((unsigned char) ds_end (&getl_buf)[-1]))
     ds_truncate (&getl_buf, ds_length (&getl_buf) - 1);
-  if (ds_length (&getl_buf) > 0 && ds_end (&getl_buf)[-1] == set_endcmd)
+  if (ds_length (&getl_buf) > 0 && ds_end (&getl_buf)[-1] == get_endcmd() )
     {
       dot = 1;
       ds_truncate (&getl_buf, ds_length (&getl_buf) - 1);
     }
   
-  for (cp = ds_value (&getl_buf); cp < ds_end (&getl_buf); )
+  for (cp = ds_c_str (&getl_buf); cp < ds_end (&getl_buf); )
     {
       if (*cp == '\'' && !in_quote)
        in_apos ^= 1;
@@ -570,18 +550,18 @@ perform_DO_REPEAT_substitutions (void)
       
       if (in_quote || in_apos || !CHAR_IS_ID1 (*cp))
        {
-         ds_putchar (&output, *cp++);
+         ds_putc (&output, *cp++);
          continue;
        }
 
       /* Collect an identifier. */
       {
-       char name[9];
+       char name[LONG_NAME_LEN + 1];
        char *start = cp;
        char *np = name;
        char *substitution;
 
-       while (CHAR_IS_IDN (*cp) && np < &name[8])
+       while (CHAR_IS_IDN (*cp) && np < &name[LONG_NAME_LEN])
          *np++ = *cp++;
        while (CHAR_IS_IDN (*cp))
          cp++;
@@ -590,59 +570,17 @@ perform_DO_REPEAT_substitutions (void)
        substitution = find_DO_REPEAT_substitution (name);
        if (!substitution)
          {
-           ds_concat_buffer (&output, start, cp - start);
+           ds_concat (&output, start, cp - start);
            continue;
          }
 
        /* Force output buffer size, copy substitution. */
-       ds_concat (&output, substitution);
+       ds_puts (&output, substitution);
       }
     }
   if (dot)
-    ds_putchar (&output, (unsigned char) set_endcmd);
+    ds_putc (&output, get_endcmd() );
 
   ds_destroy (&getl_buf);
   getl_buf = output;
 }
-\f
-/* Debugging code. */
-
-#if DEBUGGING
-static void
-debug_print (void)
-{
-  struct repeat_entry *iter;
-  int j;
-
-  printf ("DO REPEAT\n");
-  for (iter = repeat_tab; iter; iter = iter->next)
-    {
-      printf ("   %s%s=", iter->id, iter->type ? "(ids)" : "");
-      for (j = 0; j < count; j++)
-       printf ("%s ", iter->replacement[j]);
-      putc (iter->next ? '/' : '.', stdout);
-      printf ("\n");
-    }
-}
-
-static void
-debug_print_lines (void)
-{
-  struct getl_line_list *iter;
-  const char *fn = "(none)";
-  int ln = 65536;
-
-  printf ("---begin DO REPEAT lines---\n");
-  for (iter = line_buf_head; iter; iter = iter->next)
-    {
-      if (iter->len < 0)
-       {
-         ln = -iter->len;
-         fn = iter->line;
-       } else {
-         printf ("%s:%d: %s", fn, ln++, iter->line);
-       }
-    }
-  printf ("---end DO REPEAT lines---\n");
-}
-#endif /* DEBUGGING */