]> git.ipfire.org Git - thirdparty/gettext.git/commitdiff
Check syntax of obsolete entries of PO files, not only in msgmerge.
authorBruno Haible <bruno@clisp.org>
Thu, 8 Mar 2001 08:01:01 +0000 (08:01 +0000)
committerBruno Haible <bruno@clisp.org>
Thu, 8 Mar 2001 08:01:01 +0000 (08:01 +0000)
src/ChangeLog
src/po-gram-gen.y
src/po-lex.c
src/po-lex.h

index cf4062be84f58c4bef13de020a786f169e55b605..ec4aed32fb74acfab659049618fc8391be4160cc 100644 (file)
@@ -1,3 +1,28 @@
+2001-03-04  Bruno Haible  <haible@clisp.cons.org>
+
+       Check syntax of obsolete entries of PO files, not only in msgmerge.
+       * po-lex.h (pass_obsolete_entries): New declaration.
+       (msgstr_def): Remove pos field.
+       * po-lex.c (po_lex_obsolete): New variable.
+       (pass_obsolete_entries): Make non-static.
+       (lex_open): Initialize po_lex_obsolete.
+       (lex_close): Reset po_lex_obsolete.
+       (po_gram_lex): Don't look at pass_obsolete_entries. Instead, set
+       po_lex_obsolete to 1 when "#~" is seen. Reset po_lex_obsolete when
+       a newline is seen. Before returning, fill the 'pos' and 'obsolete'
+       fields of any token.
+       * po-gram.gen.y (check_obsolete): New macro.
+       (union): Add a 'pos' and 'obsolete' field for any symbol type.
+       (NAME): Assign to type <string>.
+       (DOMAIN, MSGID, MSGID_PLURAL, MSGSTR, '[', ']'): Assign to type <pos>.
+       (msgid, msgstr): Remove.
+       (message, msgid_pluralform, pluralform_list, pluralform, string_list):
+       Signal an error if the 'obsolete' field is not the same across the
+       entire token sequence of the rule.
+       (message): Deal with pass_obsolete_entries here.
+       (msgid_pluralform, pluralform_list, pluralform, string_list): Fill the
+       'pos' and 'obsolete' fields of $$.
+
 2001-03-03  Bruno Haible  <haible@clisp.cons.org>
 
        Fix parsing of strings in CJK encodings.
index ddd776da7dcf0530ba65f98a9a6424f17eb9f1be..1b576aa2eb8e9e6f2ba7554f189546f5a26dd5a0 100644 (file)
@@ -81,6 +81,11 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
 #define yycheck  po_gram_yycheck
 
 static long plural_counter;
+
+#define check_obsolete(value1,value2) \
+  if ((value1).obsolete != (value2).obsolete) \
+    po_gram_error_at_line (&(value2).pos, _("inconsistent use of #~"));
+
 %}
 
 %token COMMENT
@@ -96,15 +101,15 @@ static long plural_counter;
 
 %union
 {
-  char *string;
-  long number;
-  lex_pos_ty pos;
-  struct msgstr_def rhs;
+  struct { char *string; lex_pos_ty pos; int obsolete; } string;
+  struct { long number; lex_pos_ty pos; int obsolete; } number;
+  struct { lex_pos_ty pos; int obsolete; } pos;
+  struct { struct msgstr_def rhs; lex_pos_ty pos; int obsolete; } rhs;
 }
 
-%type <string> STRING COMMENT string_list msgid_pluralform
+%type <string> STRING COMMENT NAME string_list msgid_pluralform
 %type <number> NUMBER
-%type <pos> msgid msgstr
+%type <pos> DOMAIN MSGID MSGID_PLURAL MSGSTR '[' ']'
 %type <rhs> pluralform pluralform_list
 
 %right MSGSTR
@@ -122,45 +127,72 @@ msgfmt
 domain
        : DOMAIN STRING
                {
-                  po_callback_domain ($2);
+                  po_callback_domain ($2.string);
                }
        ;
 
 message
-       : msgid string_list msgstr string_list
+       : MSGID string_list MSGSTR string_list
                {
-                 po_callback_message ($2, &$1, NULL,
-                                      $4, strlen ($4) + 1, &$3);
+                 check_obsolete ($1, $2);
+                 check_obsolete ($1, $3);
+                 check_obsolete ($1, $4);
+                 if (!$1.obsolete || pass_obsolete_entries)
+                   po_callback_message ($2.string, &$1.pos, NULL,
+                                        $4.string, strlen ($4.string) + 1, &$3.pos);
+                 else
+                   {
+                     free ($2.string);
+                     free ($4.string);
+                   }
                }
-       | msgid string_list msgid_pluralform pluralform_list
+       | MSGID string_list msgid_pluralform pluralform_list
                {
-                 po_callback_message ($2, &$1, $3,
-                                      $4.msgstr, $4.msgstr_len, &$4.pos);
+                 check_obsolete ($1, $2);
+                 check_obsolete ($1, $3);
+                 check_obsolete ($1, $4);
+                 if (!$1.obsolete || pass_obsolete_entries)
+                   po_callback_message ($2.string, &$1.pos, $3.string,
+                                        $4.rhs.msgstr, $4.rhs.msgstr_len, &$4.pos);
+                 else
+                   {
+                     free ($2.string);
+                     free ($3.string);
+                     free ($4.rhs.msgstr);
+                   }
                }
-       | msgid string_list msgid_pluralform
+       | MSGID string_list msgid_pluralform
                {
-                 po_gram_error_at_line (&$1, _("missing `msgstr[]' section"));
-                 free ($2);
-                 free ($3);
+                 check_obsolete ($1, $2);
+                 check_obsolete ($1, $3);
+                 po_gram_error_at_line (&$1.pos, _("missing `msgstr[]' section"));
+                 free ($2.string);
+                 free ($3.string);
                }
-       | msgid string_list pluralform_list
+       | MSGID string_list pluralform_list
                {
-                 po_gram_error_at_line (&$1, _("missing `msgid_plural' section"));
-                 free ($2);
-                 free ($3.msgstr);
+                 check_obsolete ($1, $2);
+                 check_obsolete ($1, $3);
+                 po_gram_error_at_line (&$1.pos, _("missing `msgid_plural' section"));
+                 free ($2.string);
+                 free ($3.rhs.msgstr);
                }
-       | msgid string_list
+       | MSGID string_list
                {
-                 po_gram_error_at_line (&$1, _("missing `msgstr' section"));
-                 free ($2);
+                 check_obsolete ($1, $2);
+                 po_gram_error_at_line (&$1.pos, _("missing `msgstr' section"));
+                 free ($2.string);
                }
        ;
 
 msgid_pluralform
        : MSGID_PLURAL string_list
                {
+                 check_obsolete ($1, $2);
                  plural_counter = 0;
-                 $$ = $2;
+                 $$.string = $2.string;
+                 $$.pos = $1.pos;
+                 $$.obsolete = $1.obsolete;
                }
        ;
 
@@ -171,44 +203,37 @@ pluralform_list
                }
        | pluralform_list pluralform
                {
-                 $$.msgstr = (char *) xmalloc ($1.msgstr_len + $2.msgstr_len);
-                 memcpy ($$.msgstr, $1.msgstr, $1.msgstr_len);
-                 memcpy ($$.msgstr + $1.msgstr_len, $2.msgstr, $2.msgstr_len);
-                 $$.msgstr_len = $1.msgstr_len + $2.msgstr_len;
+                 check_obsolete ($1, $2);
+                 $$.rhs.msgstr = (char *) xmalloc ($1.rhs.msgstr_len + $2.rhs.msgstr_len);
+                 memcpy ($$.rhs.msgstr, $1.rhs.msgstr, $1.rhs.msgstr_len);
+                 memcpy ($$.rhs.msgstr + $1.rhs.msgstr_len, $2.rhs.msgstr, $2.rhs.msgstr_len);
+                 $$.rhs.msgstr_len = $1.rhs.msgstr_len + $2.rhs.msgstr_len;
+                 free ($1.rhs.msgstr);
+                 free ($2.rhs.msgstr);
                  $$.pos = $1.pos;
-                 free ($1.msgstr);
-                 free ($2.msgstr);
+                 $$.obsolete = $1.obsolete;
                }
        ;
 
 pluralform
-       : msgstr '[' NUMBER ']' string_list
+       : MSGSTR '[' NUMBER ']' string_list
                {
-                 if ($3 != plural_counter)
+                 check_obsolete ($1, $2);
+                 check_obsolete ($1, $3);
+                 check_obsolete ($1, $4);
+                 check_obsolete ($1, $5);
+                 if ($3.number != plural_counter)
                    {
                      if (plural_counter == 0)
-                       po_gram_error_at_line (&$1, _("first plural form has nonzero index"));
+                       po_gram_error_at_line (&$1.pos, _("first plural form has nonzero index"));
                      else
-                       po_gram_error_at_line (&$1, _("plural form has wrong index"));
+                       po_gram_error_at_line (&$1.pos, _("plural form has wrong index"));
                    }
                  plural_counter++;
-                 $$.msgstr = $5;
-                 $$.msgstr_len = strlen ($5) + 1;
-                 $$.pos = $1;
-               }
-       ;
-
-msgid
-       : MSGID
-               {
-                 $$ = gram_pos;
-               }
-       ;
-
-msgstr
-       : MSGSTR
-               {
-                 $$ = gram_pos;
+                 $$.rhs.msgstr = $5.string;
+                 $$.rhs.msgstr_len = strlen ($5.string) + 1;
+                 $$.pos = $1.pos;
+                 $$.obsolete = $1.obsolete;
                }
        ;
 
@@ -222,18 +247,21 @@ string_list
                  size_t len1;
                  size_t len2;
 
-                 len1 = strlen ($1);
-                 len2 = strlen ($2);
-                 $$ = (char *) xmalloc (len1 + len2 + 1);
-                 stpcpy (stpcpy ($$, $1), $2);
-                 free ($1);
-                 free ($2);
+                 check_obsolete ($1, $2);
+                 len1 = strlen ($1.string);
+                 len2 = strlen ($2.string);
+                 $$.string = (char *) xmalloc (len1 + len2 + 1);
+                 stpcpy (stpcpy ($$.string, $1.string), $2.string);
+                 free ($1.string);
+                 free ($2.string);
+                 $$.pos = $1.pos;
+                 $$.obsolete = $1.obsolete;
                }
        ;
 
 comment
        : COMMENT
                {
-                 po_callback_comment ($1);
+                 po_callback_comment ($1.string);
                }
        ;
index cf43fe7521377cd2ecdc58f4742e99830846e5ec..509f8020bcdb3f3a454d593aa1e6d11f43706f90 100644 (file)
 static FILE *fp;
 lex_pos_ty gram_pos;
 unsigned int gram_max_allowed_errors = 20;
+static int po_lex_obsolete;
 const char *po_lex_charset;
 #if HAVE_ICONV
 iconv_t po_lex_iconv;
 #endif
 static int pass_comments = 0;
-static int pass_obsolete_entries = 0;
+int pass_obsolete_entries = 0;
 
 
 /* Prototypes for local functions.  */
@@ -85,6 +86,7 @@ lex_open (fname)
           _("error while opening \"%s\" for reading"), fname);
 
   gram_pos.line_number = 1;
+  po_lex_obsolete = 0;
   po_lex_charset = NULL;
 #if HAVE_ICONV
   po_lex_iconv = (iconv_t)(-1);
@@ -105,6 +107,7 @@ lex_close ()
   gram_pos.file_name = 0;
   gram_pos.line_number = 0;
   error_message_count = 0;
+  po_lex_obsolete = 0;
   po_lex_charset = NULL;
 #if HAVE_ICONV
   if (po_lex_iconv != (iconv_t)(-1))
@@ -374,7 +377,7 @@ control_sequence ()
 
 
 /* Return the next token in the PO file.  The return codes are defined
-   in "po-gram-gen2.h".  Associated data is put in 'po_gram_lval.  */
+   in "po-gram-gen2.h".  Associated data is put in 'po_gram_lval'.  */
 int
 po_gram_lex ()
 {
@@ -392,27 +395,32 @@ po_gram_lex ()
          /* Yacc want this for end of file.  */
          return 0;
 
+       case '\n':
+         po_lex_obsolete = 0;
+         break;
+
        case ' ':
        case '\t':
-       case '\n':
        case '\r':
        case '\f':
        case '\v':
          break;
 
        case '#':
+         c = lex_getc ();
+         if (c == '~')
+           /* A pseudo-comment beginning with #~ is found.  This is
+              not a comment.  It is the format for obsolete entries.
+              We simply discard the "#~" prefix.  The following
+              characters are expected to be well formed.  */
+           {
+             po_lex_obsolete = 1;
+             break;
+           }
+
          /* Accumulate comments into a buffer.  If we have been asked
             to pass comments, generate a COMMENT token, otherwise
             discard it.  */
-         c = lex_getc ();
-         if (c == '~' && pass_obsolete_entries)
-           /* A special comment beginning with #~ is found.  This
-              is the format for obsolete entries and if we are
-              asked to return them is entries not as comments be
-              simply stop processing the comment here.  The
-              following characters are expected to be well formed.  */
-           break;
-
          if (pass_comments)
            {
              bufpos = 0;
@@ -431,15 +439,21 @@ po_gram_lex ()
                }
              buf[bufpos] = 0;
 
-             po_gram_lval.string = buf;
+             po_gram_lval.string.string = buf;
+             po_gram_lval.string.pos = gram_pos;
+             po_gram_lval.string.obsolete = po_lex_obsolete;
+             po_lex_obsolete = 0;
              return COMMENT;
            }
          else
-           /* We do this in separate loop because collecting large
-              comments while they get not passed to the upper layers
-              is not very effective.  */
-           while (c != EOF && c != '\n')
-             c = lex_getc ();
+           {
+             /* We do this in separate loop because collecting large
+                comments while they get not passed to the upper layers
+                is not very effective.  */
+             while (c != EOF && c != '\n')
+               c = lex_getc ();
+             po_lex_obsolete = 0;
+           }
          break;
 
        case '"':
@@ -519,7 +533,9 @@ po_gram_lex ()
            buf[bufpos] = 0;
 
            /* FIXME: Treatment of embedded \000 chars is incorrect.  */
-           po_gram_lval.string = xstrdup (buf);
+           po_gram_lval.string.string = xstrdup (buf);
+           po_gram_lval.string.pos = gram_pos;
+           po_gram_lval.string.obsolete = po_lex_obsolete;
            return STRING;
          }
 
@@ -576,12 +592,20 @@ po_gram_lex ()
 
          c = keyword_p (buf);
          if (c == NAME)
-           po_gram_lval.string = xstrdup (buf);
+           {
+             po_gram_lval.string.string = xstrdup (buf);
+             po_gram_lval.string.pos = gram_pos;
+             po_gram_lval.string.obsolete = po_lex_obsolete;
+           }
+         else
+           {
+             po_gram_lval.pos.pos = gram_pos;
+             po_gram_lval.pos.obsolete = po_lex_obsolete;
+           }
          return c;
 
        case '0': case '1': case '2': case '3': case '4':
        case '5': case '6': case '7': case '8': case '9':
-         /* I know, we don't need numbers, yet.  */
          bufpos = 0;
          for (;;)
            {
@@ -608,13 +632,19 @@ po_gram_lex ()
 
          buf[bufpos] = 0;
 
-         po_gram_lval.number = atol (buf);
+         po_gram_lval.number.number = atol (buf);
+         po_gram_lval.number.pos = gram_pos;
+         po_gram_lval.number.obsolete = po_lex_obsolete;
          return NUMBER;
 
        case '[':
+         po_gram_lval.pos.pos = gram_pos;
+         po_gram_lval.pos.obsolete = po_lex_obsolete;
          return '[';
 
        case ']':
+         po_gram_lval.pos.pos = gram_pos;
+         po_gram_lval.pos.obsolete = po_lex_obsolete;
          return ']';
 
        default:
index 4beb7bc640d7cd1d3887047bb6ec9a5a982b813a..279382ad464b52a7c4ce392d3d9ac51dd9e2d4ce 100644 (file)
@@ -47,6 +47,9 @@ extern const char *po_lex_charset;
 extern iconv_t po_lex_iconv;
 #endif
 
+/* Nonzero if obsolete entries shall be considered as valid.  */
+extern int pass_obsolete_entries;
+
 
 /* Open the PO file FNAME and prepare its lexical analysis.  */
 extern void lex_open PARAMS ((const char *__fname));
@@ -138,7 +141,6 @@ struct msgstr_def
 {
   char *msgstr;
   size_t msgstr_len;
-  lex_pos_ty pos;
 };
 
 #endif