Update Traditional Chinese translation for the binutils sub-directory.
[deliverable/binutils-gdb.git] / binutils / rclex.c
index edcf2cece6b30cbdca2348accc23293103b22fe5..d6a0f91c7d16cd9ae0312687dd0c9532529954f1 100644 (file)
@@ -1,7 +1,6 @@
 /* rclex.c -- lexer for Windows rc files parser  */
 
-/* Copyright 1997, 1998, 1999, 2001, 2002, 2003, 2005, 2006, 2007
-   Free Software Foundation, Inc.
+/* Copyright (C) 1997-2020 Free Software Foundation, Inc.
 
    Written by Kai Tietz, Onevision.
 
@@ -9,7 +8,7 @@
 
    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
-   the Free Software Foundation; either version 2 of the License, or
+   the Free Software Foundation; either version 3 of the License, or
    (at your option) any later version.
 
    This program is distributed in the hope that it will be useful,
@@ -22,6 +21,7 @@
    Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, MA
    02110-1301, USA.  */
 
+
 /* This is a lexer used by the Windows rc file parser.  It basically
    just recognized a bunch of keywords.  */
 
@@ -40,7 +40,7 @@
 
 static int rcdata_mode;
 
-/* Whether we are supressing lines from cpp (including windows.h or
+/* Whether we are suppressing lines from cpp (including windows.h or
    headers from your C sources may bring in externs and typedefs).
    When active, we return IGNORED_TOKEN, which lets us ignore these
    outside of resource constructs.  Thus, it isn't required to protect
@@ -142,11 +142,64 @@ cpp_line (void)
   const char *s = rclex_tok;
   int line;
   char *send, *fn;
+  size_t len, mlen;
 
   ++s;
   while (ISSPACE (*s))
     ++s;
-  
+
+  /* Check for #pragma code_page ( DEFAULT | <nr>).  */
+  len = strlen (s);
+  mlen = strlen ("pragma");
+  if (len > mlen && memcmp (s, "pragma", mlen) == 0 && ISSPACE (s[mlen]))
+    {
+      const char *end;
+
+      s += mlen + 1;
+      while (ISSPACE (*s))
+       ++s;
+      len = strlen (s);
+      mlen = strlen ("code_page");
+      if (len <= mlen || memcmp (s, "code_page", mlen) != 0)
+       /* FIXME: We ought to issue a warning message about an unrecognised pragma.  */
+       return;
+      s += mlen;
+      while (ISSPACE (*s))
+       ++s;
+      if (*s != '(')
+       /* FIXME: We ought to issue an error message about a malformed pragma.  */
+       return;
+      ++s;
+      while (ISSPACE (*s))
+       ++s;
+      if (*s == 0 || (end = strchr (s, ')')) == NULL)
+       /* FIXME: We ought to issue an error message about a malformed pragma.  */
+       return;
+      len = (size_t) (end - s);
+      fn = xmalloc (len + 1);
+      if (len)
+       memcpy (fn, s, len);
+      fn[len] = 0;
+      while (len > 0 && (fn[len - 1] > 0 && fn[len - 1] <= 0x20))
+       fn[--len] = 0;
+      if (! len || (len == strlen ("DEFAULT") && strcasecmp (fn, "DEFAULT") == 0))
+       wind_current_codepage = wind_default_codepage;
+      else if (len > 0)
+       {
+         rc_uint_type ncp;
+
+         if (fn[0] == '0' && (fn[1] == 'x' || fn[1] == 'X'))
+             ncp = (rc_uint_type) strtol (fn + 2, NULL, 16);
+         else
+             ncp = (rc_uint_type) strtol (fn, NULL, 10);
+         if (ncp == CP_UTF16 || ! unicode_is_valid_codepage (ncp))
+           fatal (_("invalid value specified for pragma code_page.\n"));
+         wind_current_codepage = ncp;
+       }
+      free (fn);
+      return;
+    }
+
   line = strtol (s, &send, 0);
   if (*send != '\0' && ! ISSPACE (*send))
     return;
@@ -336,9 +389,9 @@ handle_quotes (rc_uint_type *len)
        }
       else
        {
-         rcparse_warning ("unexpected character after '\"'");
          ++t;
-         assert (ISSPACE (*t));
+         if (! ISSPACE (*t))
+           rcparse_warning ("unexpected character after '\"'");
          while (ISSPACE (*t))
            {
              if ((*t) == '\n')
@@ -625,7 +678,7 @@ static void
 rclex_string (void)
 {
   int c;
-  
+
   while ((c = rclex_peekch ()) != -1)
     {
       if (c == '\n')
@@ -639,6 +692,18 @@ rclex_string (void)
         }
       else if (rclex_readch () == '"')
        {
+         /* PR 6714
+            Skip any whitespace after the end of the double quotes.  */
+         do
+           {
+             c = rclex_peekch ();
+             if (ISSPACE (c))
+               rclex_readch ();
+             else
+               c = -1;
+           }
+         while (c != -1);
+
          if (rclex_peekch () == '"')
            rclex_readch ();
          else
@@ -716,7 +781,7 @@ yylex (void)
          /* Clear token.  */
          rclex_tok_pos = 0;
          rclex_tok[0] = 0;
-         
+
          if ((ch = rclex_readch ()) == -1)
            return -1;
          if (ch == '\n')
@@ -732,15 +797,15 @@ yylex (void)
          cpp_line ();
          ch = IGNORED_TOKEN;
          break;
-       
+
        case '{':
          ch = IGNORE_CPP (BEG);
          break;
-       
+
        case '}':
          ch = IGNORE_CPP (END);
          break;
-       
+
        case '0': case '1': case '2': case '3': case '4':
        case '5': case '6': case '7': case '8': case '9':
          yylval.i.val = read_digit (ch);
@@ -790,7 +855,11 @@ yylex (void)
        default:
          if (ISIDST (ch) || ch=='$')
            {
-             while ((ch = rclex_peekch ()) != -1 && (ISIDNUM (ch) || ch == '$' || ch == '.'))
+             while ((ch = rclex_peekch ()) != -1
+                    && (ISIDNUM (ch) || ch == '$' || ch == '.'
+                        || ch == ':' || ch == '\\' || ch == '/'
+                        || ch == '_' || ch == '-')
+                   )
                rclex_readch ();
              ch = IGNORE_CPP (rclex_translatekeyword (rclex_tok));
              if (ch == STRING)
This page took 0.025248 seconds and 4 git commands to generate.