]> git.ipfire.org Git - thirdparty/gcc.git/blobdiff - libcpp/directives.c
* config/microblaze/microblaze.c (microblaze_expand_block_move): Treat
[thirdparty/gcc.git] / libcpp / directives.c
index 7f7216265c922d208414ef42d0d9d33ed12dc32d..1ada834da17482ebd75fd9ed57312b0e41cd24a7 100644 (file)
@@ -1,14 +1,12 @@
 /* CPP Library. (Directive handling.)
-   Copyright (C) 1986, 1987, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998,
-   1999, 2000, 2001, 2002, 2003, 2004, 2005,
-   2007 Free Software Foundation, Inc.
+   Copyright (C) 1986-2019 Free Software Foundation, Inc.
    Contributed by Per Bothner, 1994-95.
    Based on CCCP program by Paul Rubin, June 1986
    Adapted to ANSI C, Richard Stallman, Jan 1987
 
 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, or (at your option) any
+Free Software Foundation; either version 3, or (at your option) any
 later version.
 
 This program is distributed in the hope that it will be useful,
@@ -17,8 +15,8 @@ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 GNU General Public License for more details.
 
 You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.  */
+along with this program; see the file COPYING3.  If not see
+<http://www.gnu.org/licenses/>.  */
 
 #include "config.h"
 #include "system.h"
@@ -32,7 +30,7 @@ Foundation, 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.  */
 struct if_stack
 {
   struct if_stack *next;
-  unsigned int line;           /* Line where condition started.  */
+  location_t line;             /* Line where condition started.  */
   const cpp_hashnode *mi_cmacro;/* macro name for #ifndef around entire file */
   bool skip_elses;             /* Can future #else / #elif be skipped?  */
   bool was_skipping;           /* If were skipping on entry.  */
@@ -75,6 +73,7 @@ struct pragma_entry
 #define INCL           (1 << 2)
 #define IN_I           (1 << 3)
 #define EXPAND         (1 << 4)
+#define DEPRECATED     (1 << 5)
 
 /* Defines one #-directive, including how to handle it.  */
 typedef void (*directive_handler) (cpp_reader *);
@@ -91,18 +90,20 @@ struct directive
 /* Forward declarations.  */
 
 static void skip_rest_of_line (cpp_reader *);
-static void check_eol (cpp_reader *);
+static void check_eol (cpp_reader *, bool);
 static void start_directive (cpp_reader *);
 static void prepare_directive_trad (cpp_reader *);
 static void end_directive (cpp_reader *, int);
 static void directive_diagnostics (cpp_reader *, const directive *, int);
 static void run_directive (cpp_reader *, int, const char *, size_t);
 static char *glue_header_name (cpp_reader *);
-static const char *parse_include (cpp_reader *, int *, const cpp_token ***);
+static const char *parse_include (cpp_reader *, int *, const cpp_token ***,
+                                 location_t *);
 static void push_conditional (cpp_reader *, int, int, const cpp_hashnode *);
 static unsigned int read_flag (cpp_reader *, unsigned int);
-static int strtoul_for_line (const uchar *, unsigned int, unsigned long *);
-static void do_diagnostic (cpp_reader *, int, int);
+static bool strtolinenum (const uchar *, size_t, linenum_type *, bool *);
+static void do_diagnostic (cpp_reader *, enum cpp_diagnostic_level code,
+                          enum cpp_warning_reason reason, int);
 static cpp_hashnode *lex_macro_node (cpp_reader *, bool);
 static int undefine_macros (cpp_reader *, cpp_hashnode *, void *);
 static void do_include_common (cpp_reader *, enum include_type);
@@ -116,44 +117,46 @@ static void do_pragma_once (cpp_reader *);
 static void do_pragma_poison (cpp_reader *);
 static void do_pragma_system_header (cpp_reader *);
 static void do_pragma_dependency (cpp_reader *);
+static void do_pragma_warning_or_error (cpp_reader *, bool error);
+static void do_pragma_warning (cpp_reader *);
+static void do_pragma_error (cpp_reader *);
 static void do_linemarker (cpp_reader *);
 static const cpp_token *get_token_no_padding (cpp_reader *);
 static const cpp_token *get__Pragma_string (cpp_reader *);
-static void destringize_and_run (cpp_reader *, const cpp_string *);
-static int parse_answer (cpp_reader *, struct answer **, int);
-static cpp_hashnode *parse_assertion (cpp_reader *, struct answer **, int);
-static struct answer ** find_answer (cpp_hashnode *, const struct answer *);
+static void destringize_and_run (cpp_reader *, const cpp_string *,
+                                location_t);
+static bool parse_answer (cpp_reader *, int, location_t, cpp_macro **);
+static cpp_hashnode *parse_assertion (cpp_reader *, int, cpp_macro **);
+static cpp_macro **find_answer (cpp_hashnode *, const cpp_macro *);
 static void handle_assertion (cpp_reader *, const char *, int);
+static void do_pragma_push_macro (cpp_reader *);
+static void do_pragma_pop_macro (cpp_reader *);
+static void cpp_pop_definition (cpp_reader *, struct def_pragma_macro *);
 
-/* This is the table of directive handlers.  It is ordered by
-   frequency of occurrence; the numbers at the end are directive
-   counts from all the source code I have lying around (egcs and libc
-   CVS as of 1999-05-18, plus grub-0.5.91, linux-2.2.9, and
-   pcmcia-cs-3.0.9).  This is no longer important as directive lookup
-   is now O(1).  All extensions other than #warning and #include_next
-   are deprecated.  The name is where the extension appears to have
-   come from.  */
+/* This is the table of directive handlers.  All extensions other than
+   #warning, #include_next, and #import are deprecated.  The name is
+   where the extension appears to have come from.  */
 
 #define DIRECTIVE_TABLE                                                        \
-D(define,      T_DEFINE = 0,   KANDR,     IN_I)           /* 270554 */ \
-D(include,     T_INCLUDE,      KANDR,     INCL | EXPAND)  /*  52262 */ \
-D(endif,       T_ENDIF,        KANDR,     COND)           /*  45855 */ \
-D(ifdef,       T_IFDEF,        KANDR,     COND | IF_COND) /*  22000 */ \
-D(if,          T_IF,           KANDR, COND | IF_COND | EXPAND) /*  18162 */ \
-D(else,                T_ELSE,         KANDR,     COND)           /*   9863 */ \
-D(ifndef,      T_IFNDEF,       KANDR,     COND | IF_COND) /*   9675 */ \
-D(undef,       T_UNDEF,        KANDR,     IN_I)           /*   4837 */ \
-D(line,                T_LINE,         KANDR,     EXPAND)         /*   2465 */ \
-D(elif,                T_ELIF,         STDC89,    COND | EXPAND)  /*    610 */ \
-D(error,       T_ERROR,        STDC89,    0)              /*    475 */ \
-D(pragma,      T_PRAGMA,       STDC89,    IN_I)           /*    195 */ \
-D(warning,     T_WARNING,      EXTENSION, 0)              /*     22 */ \
-D(include_next,        T_INCLUDE_NEXT, EXTENSION, INCL | EXPAND)  /*     19 */ \
-D(ident,       T_IDENT,        EXTENSION, IN_I)           /*     11 */ \
-D(import,      T_IMPORT,       EXTENSION, INCL | EXPAND)  /* 0 ObjC */ \
-D(assert,      T_ASSERT,       EXTENSION, 0)              /* 0 SVR4 */ \
-D(unassert,    T_UNASSERT,     EXTENSION, 0)              /* 0 SVR4 */ \
-D(sccs,                T_SCCS,         EXTENSION, IN_I)           /* 0 SVR4? */
+  D(define,    T_DEFINE = 0,   KANDR,     IN_I)                        \
+  D(include,   T_INCLUDE,      KANDR,     INCL | EXPAND)               \
+  D(endif,     T_ENDIF,        KANDR,     COND)                        \
+  D(ifdef,     T_IFDEF,        KANDR,     COND | IF_COND)              \
+  D(if,                T_IF,           KANDR,     COND | IF_COND | EXPAND)     \
+  D(else,      T_ELSE,         KANDR,     COND)                        \
+  D(ifndef,    T_IFNDEF,       KANDR,     COND | IF_COND)              \
+  D(undef,     T_UNDEF,        KANDR,     IN_I)                        \
+  D(line,      T_LINE,         KANDR,     EXPAND)                      \
+  D(elif,      T_ELIF,         STDC89,    COND | EXPAND)               \
+  D(error,     T_ERROR,        STDC89,    0)                           \
+  D(pragma,    T_PRAGMA,       STDC89,    IN_I)                        \
+  D(warning,   T_WARNING,      EXTENSION, 0)                           \
+  D(include_next, T_INCLUDE_NEXT, EXTENSION, INCL | EXPAND)            \
+  D(ident,     T_IDENT,        EXTENSION, IN_I)                        \
+  D(import,    T_IMPORT,       EXTENSION, INCL | EXPAND)  /* ObjC */   \
+  D(assert,    T_ASSERT,       EXTENSION, DEPRECATED)     /* SVR4 */   \
+  D(unassert,  T_UNASSERT,     EXTENSION, DEPRECATED)     /* SVR4 */   \
+  D(sccs,      T_SCCS,         EXTENSION, IN_I)           /*  SVR4? */
 
 /* #sccs is synonymous with #ident.  */
 #define do_sccs do_ident
@@ -181,6 +184,16 @@ static const directive dtable[] =
 DIRECTIVE_TABLE
 };
 #undef D
+
+/* A NULL-terminated array of directive names for use
+   when suggesting corrections for misspelled directives.  */
+#define D(name, t, origin, flags) #name,
+static const char * const directive_names[] = {
+DIRECTIVE_TABLE
+  NULL
+};
+#undef D
+
 #undef DIRECTIVE_TABLE
 
 /* Wrapper struct directive for linemarkers.
@@ -188,11 +201,9 @@ DIRECTIVE_TABLE
    did use this notation in its preprocessed output.  */
 static const directive linemarker_dir =
 {
-  do_linemarker, U"#", 1, KANDR, IN_I
+  do_linemarker, UC"#", 1, KANDR, IN_I
 };
 
-#define SEEN_EOL() (pfile->cur_token[-1].type == CPP_EOF)
-
 /* Skip any remaining tokens in a directive.  */
 static void
 skip_rest_of_line (cpp_reader *pfile)
@@ -207,13 +218,33 @@ skip_rest_of_line (cpp_reader *pfile)
       ;
 }
 
-/* Ensure there are no stray tokens at the end of a directive.  */
+/* Helper function for check_oel.  */
+
 static void
-check_eol (cpp_reader *pfile)
+check_eol_1 (cpp_reader *pfile, bool expand, enum cpp_warning_reason reason)
 {
-  if (! SEEN_EOL () && _cpp_lex_token (pfile)->type != CPP_EOF)
-    cpp_error (pfile, CPP_DL_PEDWARN, "extra tokens at end of #%s directive",
-              pfile->directive->name);
+  if (! SEEN_EOL () && (expand
+                       ? cpp_get_token (pfile)
+                       : _cpp_lex_token (pfile))->type != CPP_EOF)
+    cpp_pedwarning (pfile, reason, "extra tokens at end of #%s directive",
+                   pfile->directive->name);
+}
+
+/* Variant of check_eol used for Wendif-labels warnings.  */
+
+static void
+check_eol_endif_labels (cpp_reader *pfile)
+{
+  check_eol_1 (pfile, false, CPP_W_ENDIF_LABELS);
+}
+
+/* Ensure there are no stray tokens at the end of a directive.  If
+   EXPAND is true, tokens macro-expanding to nothing are allowed.  */
+
+static void
+check_eol (cpp_reader *pfile, bool expand)
+{
+  check_eol_1 (pfile, expand, CPP_W_NONE);
 }
 
 /* Ensure there are no stray tokens other than comments at the end of
@@ -273,16 +304,17 @@ start_directive (cpp_reader *pfile)
 static void
 end_directive (cpp_reader *pfile, int skip_line)
 {
-  if (pfile->state.in_deferred_pragma)
-    ;
-  else if (CPP_OPTION (pfile, traditional))
+  if (CPP_OPTION (pfile, traditional))
     {
       /* Revert change of prepare_directive_trad.  */
-      pfile->state.prevent_expansion--;
+      if (!pfile->state.in_deferred_pragma)
+       pfile->state.prevent_expansion--;
 
       if (pfile->directive != &dtable[T_DEFINE])
        _cpp_remove_overlay (pfile);
     }
+  else if (pfile->state.in_deferred_pragma)
+    ;
   /* We don't skip for an assembler #.  */
   else if (skip_line)
     {
@@ -319,7 +351,7 @@ prepare_directive_trad (cpp_reader *pfile)
 
       if (no_expand)
        pfile->state.prevent_expansion++;
-      _cpp_scan_out_logical_line (pfile, NULL);
+      _cpp_scan_out_logical_line (pfile, NULL, false);
       if (no_expand)
        pfile->state.prevent_expansion--;
 
@@ -337,11 +369,20 @@ prepare_directive_trad (cpp_reader *pfile)
 static void
 directive_diagnostics (cpp_reader *pfile, const directive *dir, int indented)
 {
-  /* Issue -pedantic warnings for extensions.  */
-  if (CPP_PEDANTIC (pfile)
-      && ! pfile->state.skipping
-      && dir->origin == EXTENSION)
-    cpp_error (pfile, CPP_DL_PEDWARN, "#%s is a GCC extension", dir->name);
+  /* Issue -pedantic or deprecated warnings for extensions.  We let
+     -pedantic take precedence if both are applicable.  */
+  if (! pfile->state.skipping)
+    {
+      if (dir->origin == EXTENSION
+         && !(dir == &dtable[T_IMPORT] && CPP_OPTION (pfile, objc))
+         && CPP_PEDANTIC (pfile))
+       cpp_error (pfile, CPP_DL_PEDWARN, "#%s is a GCC extension", dir->name);
+      else if (((dir->flags & DEPRECATED) != 0
+               || (dir == &dtable[T_IMPORT] && !CPP_OPTION (pfile, objc)))
+              && CPP_OPTION (pfile, cpp_warn_deprecated))
+       cpp_warning (pfile, CPP_W_DEPRECATED,
+                     "#%s is a deprecated GCC extension", dir->name);
+    }
 
   /* Traditionally, a directive is ignored unless its # is in
      column 1.  Therefore in code intended to work with K+R
@@ -352,16 +393,16 @@ directive_diagnostics (cpp_reader *pfile, const directive *dir, int indented)
   if (CPP_WTRADITIONAL (pfile))
     {
       if (dir == &dtable[T_ELIF])
-       cpp_error (pfile, CPP_DL_WARNING,
-                  "suggest not using #elif in traditional C");
+       cpp_warning (pfile, CPP_W_TRADITIONAL,
+                    "suggest not using #elif in traditional C");
       else if (indented && dir->origin == KANDR)
-       cpp_error (pfile, CPP_DL_WARNING,
-                  "traditional C ignores #%s with the # indented",
-                  dir->name);
+       cpp_warning (pfile, CPP_W_TRADITIONAL,
+                    "traditional C ignores #%s with the # indented",
+                    dir->name);
       else if (!indented && dir->origin != KANDR)
-       cpp_error (pfile, CPP_DL_WARNING,
-                  "suggest hiding #%s from traditional C with an indented #",
-                  dir->name);
+       cpp_warning (pfile, CPP_W_TRADITIONAL,
+                    "suggest hiding #%s from traditional C with an indented #",
+                    dir->name);
     }
 }
 
@@ -384,7 +425,7 @@ _cpp_handle_directive (cpp_reader *pfile, int indented)
 
   if (was_parsing_args)
     {
-      if (CPP_OPTION (pfile, pedantic))
+      if (CPP_OPTION (pfile, cpp_pedantic))
        cpp_error (pfile, CPP_DL_PEDWARN,
             "embedding a directive within macro arguments is not portable");
       pfile->state.parsing_args = 0;
@@ -395,8 +436,8 @@ _cpp_handle_directive (cpp_reader *pfile, int indented)
 
   if (dname->type == CPP_NAME)
     {
-      if (dname->val.node->is_directive)
-       dir = &dtable[dname->val.node->directive_index];
+      if (dname->val.node.node->is_directive)
+       dir = &dtable[dname->val.node.node->directive_index];
     }
   /* We do not recognize the # followed by a number extension in
      assembler code.  */
@@ -428,7 +469,7 @@ _cpp_handle_directive (cpp_reader *pfile, int indented)
         
         We exclude the -fdirectives-only case because macro expansion
         has not been performed yet, and block comments can cause spaces
-        to preceed the directive.  */
+        to precede the directive.  */
       if (CPP_OPTION (pfile, preprocessed)
          && !CPP_OPTION (pfile, directives_only)
          && (indented || !(dir->flags & IN_I)))
@@ -461,8 +502,35 @@ _cpp_handle_directive (cpp_reader *pfile, int indented)
       if (CPP_OPTION (pfile, lang) == CLK_ASM)
        skip = 0;
       else if (!pfile->state.skipping)
-       cpp_error (pfile, CPP_DL_ERROR, "invalid preprocessing directive #%s",
-                  cpp_token_as_text (pfile, dname));
+       {
+         const char *unrecognized
+           = (const char *)cpp_token_as_text (pfile, dname);
+         const char *hint = NULL;
+
+         /* Call back into gcc to get a spelling suggestion.  Ideally
+            we'd just use best_match from gcc/spellcheck.h (and filter
+            out the uncommon directives), but that requires moving it
+            to a support library.  */
+         if (pfile->cb.get_suggestion)
+           hint = pfile->cb.get_suggestion (pfile, unrecognized,
+                                            directive_names);
+
+         if (hint)
+           {
+             rich_location richloc (pfile->line_table, dname->src_loc);
+             source_range misspelled_token_range
+               = get_range_from_loc (pfile->line_table, dname->src_loc);
+             richloc.add_fixit_replace (misspelled_token_range, hint);
+             cpp_error_at (pfile, CPP_DL_ERROR, &richloc,
+                           "invalid preprocessing directive #%s;"
+                           " did you mean #%s?",
+                           unrecognized, hint);
+           }
+         else
+           cpp_error (pfile, CPP_DL_ERROR,
+                      "invalid preprocessing directive #%s",
+                      unrecognized);
+       }
     }
 
   pfile->directive = dir;
@@ -475,7 +543,7 @@ _cpp_handle_directive (cpp_reader *pfile, int indented)
     _cpp_backup_tokens (pfile, 1);
 
   end_directive (pfile, skip);
-  if (was_parsing_args)
+  if (was_parsing_args && !pfile->state.in_deferred_pragma)
     {
       /* Restore state when within macro args.  */
       pfile->state.parsing_args = 2;
@@ -525,18 +593,23 @@ lex_macro_node (cpp_reader *pfile, bool is_def_or_undef)
 
   if (token->type == CPP_NAME)
     {
-      cpp_hashnode *node = token->val.node;
+      cpp_hashnode *node = token->val.node.node;
 
       if (is_def_or_undef && node == pfile->spec_nodes.n_defined)
        cpp_error (pfile, CPP_DL_ERROR,
                   "\"defined\" cannot be used as a macro name");
+      else if (is_def_or_undef
+           && (node == pfile->spec_nodes.n__has_include__
+            || node == pfile->spec_nodes.n__has_include_next__))
+       cpp_error (pfile, CPP_DL_ERROR,
+                  "\"__has_include__\" cannot be used as a macro name");
       else if (! (node->flags & NODE_POISONED))
        return node;
     }
   else if (token->flags & NAMED_OP)
     cpp_error (pfile, CPP_DL_ERROR,
        "\"%s\" cannot be used as a macro name as it is an operator in C++",
-              NODE_NAME (token->val.node));
+              NODE_NAME (token->val.node.node));
   else if (token->type == CPP_EOF)
     cpp_error (pfile, CPP_DL_ERROR, "no macro name given in #%s directive",
               pfile->directive->name);
@@ -559,9 +632,14 @@ do_define (cpp_reader *pfile)
       pfile->state.save_comments =
        ! CPP_OPTION (pfile, discard_comments_in_macro_exp);
 
+      if (pfile->cb.before_define)
+       pfile->cb.before_define (pfile);
+
       if (_cpp_create_definition (pfile, node))
        if (pfile->cb.define)
          pfile->cb.define (pfile, pfile->directive_line, node);
+
+      node->flags &= ~NODE_USED;
     }
 }
 
@@ -573,16 +651,24 @@ do_undef (cpp_reader *pfile)
 
   if (node)
     {
+      if (pfile->cb.before_define)
+       pfile->cb.before_define (pfile);
+
       if (pfile->cb.undef)
        pfile->cb.undef (pfile, pfile->directive_line, node);
 
       /* 6.10.3.5 paragraph 2: [#undef] is ignored if the specified
         identifier is not currently defined as a macro name.  */
-      if (node->type == NT_MACRO)
+      if (cpp_macro_p (node))
        {
          if (node->flags & NODE_WARN)
            cpp_error (pfile, CPP_DL_WARNING,
                       "undefining \"%s\"", NODE_NAME (node));
+         else if (cpp_builtin_macro_p (node)
+                  && CPP_OPTION (pfile, warn_builtin_macro_redefined))
+           cpp_warning_with_line (pfile, CPP_W_BUILTIN_MACRO_REDEFINED,
+                                  pfile->directive_line, 0,
+                                  "undefining \"%s\"", NODE_NAME (node));
 
          if (CPP_OPTION (pfile, warn_unused_macros))
            _cpp_warn_if_unused_macro (pfile, node, NULL);
@@ -591,7 +677,7 @@ do_undef (cpp_reader *pfile)
        }
     }
 
-  check_eol (pfile);
+  check_eol (pfile, false);
 }
 
 /* Undefine a single macro/assertion/whatever.  */
@@ -603,7 +689,8 @@ undefine_macros (cpp_reader *pfile ATTRIBUTE_UNUSED, cpp_hashnode *h,
   /* Body of _cpp_free_definition inlined here for speed.
      Macros and assertions no longer have anything to free.  */
   h->type = NT_VOID;
-  h->flags &= ~(NODE_POISONED|NODE_BUILTIN|NODE_DISABLED);
+  h->value.answers = NULL;
+  h->flags &= ~(NODE_POISONED|NODE_DISABLED|NODE_USED);
   return 1;
 }
 
@@ -662,17 +749,21 @@ glue_header_name (cpp_reader *pfile)
 
 /* Returns the file name of #include, #include_next, #import and
    #pragma dependency.  The string is malloced and the caller should
-   free it.  Returns NULL on error.  */
+   free it.  Returns NULL on error.  LOCATION is the source location
+   of the file name.  */
+
 static const char *
 parse_include (cpp_reader *pfile, int *pangle_brackets,
-              const cpp_token ***buf)
+              const cpp_token ***buf, location_t *location)
 {
   char *fname;
   const cpp_token *header;
 
   /* Allow macro expansion.  */
   header = get_token_no_padding (pfile);
-  if (header->type == CPP_STRING || header->type == CPP_HEADER_NAME)
+  *location = header->src_loc;
+  if ((header->type == CPP_STRING && header->val.str.text[0] != 'R')
+      || header->type == CPP_HEADER_NAME)
     {
       fname = XNEWVEC (char, header->val.str.len - 1);
       memcpy (fname, header->val.str.text + 1, header->val.str.len - 2);
@@ -689,7 +780,7 @@ parse_include (cpp_reader *pfile, int *pangle_brackets,
       const unsigned char *dir;
 
       if (pfile->directive == &dtable[T_PRAGMA])
-       dir = U"pragma dependency";
+       dir = UC"pragma dependency";
       else
        dir = pfile->directive->name;
       cpp_error (pfile, CPP_DL_ERROR, "#%s expects \"FILENAME\" or <FILENAME>",
@@ -703,7 +794,7 @@ parse_include (cpp_reader *pfile, int *pangle_brackets,
       /* This pragma allows extra tokens after the file name.  */
     }
   else if (buf == NULL || CPP_OPTION (pfile, discard_comments))
-    check_eol (pfile);
+    check_eol (pfile, true);
   else
     {
       /* If we are not discarding comments, then gather them while
@@ -721,28 +812,23 @@ do_include_common (cpp_reader *pfile, enum include_type type)
   const char *fname;
   int angle_brackets;
   const cpp_token **buf = NULL;
+  location_t location;
 
   /* Re-enable saving of comments if requested, so that the include
      callback can dump comments which follow #include.  */
   pfile->state.save_comments = ! CPP_OPTION (pfile, discard_comments);
 
-  fname = parse_include (pfile, &angle_brackets, &buf);
+  fname = parse_include (pfile, &angle_brackets, &buf, &location);
   if (!fname)
-    {
-      if (buf)
-       XDELETEVEC (buf);
-      return;
-    }
+    goto done;
 
   if (!*fname)
-  {
-    cpp_error (pfile, CPP_DL_ERROR, "empty filename in #%s",
-               pfile->directive->name);
-    XDELETEVEC (fname);
-    if (buf)
-      XDELETEVEC (buf);
-    return;
-  }
+    {
+      cpp_error_with_line (pfile, CPP_DL_ERROR, location, 0,
+                          "empty filename in #%s",
+                          pfile->directive->name);
+      goto done;
+    }
 
   /* Prevent #include recursion.  */
   if (pfile->line_table->depth >= CPP_STACK_MAX)
@@ -757,9 +843,10 @@ do_include_common (cpp_reader *pfile, enum include_type type)
                           pfile->directive->name, fname, angle_brackets,
                           buf);
 
-      _cpp_stack_include (pfile, fname, angle_brackets, type);
+      _cpp_stack_include (pfile, fname, angle_brackets, type, location);
     }
 
+ done:
   XDELETEVEC (fname);
   if (buf)
     XDELETEVEC (buf);
@@ -819,23 +906,30 @@ read_flag (cpp_reader *pfile, unsigned int last)
 }
 
 /* Subroutine of do_line and do_linemarker.  Convert a number in STR,
-   of length LEN, to binary; store it in NUMP, and return 0 if the
-   number was well-formed, 1 if not.  Temporary, hopefully.  */
-static int
-strtoul_for_line (const uchar *str, unsigned int len, long unsigned int *nump)
+   of length LEN, to binary; store it in NUMP, and return false if the
+   number was well-formed, true if not. WRAPPED is set to true if the
+   number did not fit into 'unsigned long'.  */
+static bool
+strtolinenum (const uchar *str, size_t len, linenum_type *nump, bool *wrapped)
 {
-  unsigned long reg = 0;
+  linenum_type reg = 0;
+  linenum_type reg_prev = 0;
+
   uchar c;
+  *wrapped = false;
   while (len--)
     {
       c = *str++;
       if (!ISDIGIT (c))
-       return 1;
+       return true;
       reg *= 10;
       reg += c - '0';
+      if (reg < reg_prev) 
+       *wrapped = true;
+      reg_prev = reg;
     }
   *nump = reg;
-  return 0;
+  return false;
 }
 
 /* Interpret #line command.
@@ -844,43 +938,49 @@ strtoul_for_line (const uchar *str, unsigned int len, long unsigned int *nump)
 static void
 do_line (cpp_reader *pfile)
 {
-  const struct line_maps *line_table = pfile->line_table;
-  const struct line_map *map = &line_table->maps[line_table->used - 1];
+  struct line_maps *line_table = pfile->line_table;
+  const line_map_ordinary *map = LINEMAPS_LAST_ORDINARY_MAP (line_table);
 
   /* skip_rest_of_line() may cause line table to be realloc()ed so note down
      sysp right now.  */
 
-  unsigned char map_sysp = map->sysp;
+  unsigned char map_sysp = ORDINARY_MAP_IN_SYSTEM_HEADER_P (map);
   const cpp_token *token;
-  const char *new_file = map->to_file;
-  unsigned long new_lineno;
+  const char *new_file = ORDINARY_MAP_FILE_NAME (map);
+  linenum_type new_lineno;
 
   /* C99 raised the minimum limit on #line numbers.  */
-  unsigned int cap = CPP_OPTION (pfile, c99) ? 2147483647 : 32767;
+  linenum_type cap = CPP_OPTION (pfile, c99) ? 2147483647 : 32767;
+  bool wrapped;
 
   /* #line commands expand macros.  */
   token = cpp_get_token (pfile);
   if (token->type != CPP_NUMBER
-      || strtoul_for_line (token->val.str.text, token->val.str.len,
-                          &new_lineno))
+      || strtolinenum (token->val.str.text, token->val.str.len,
+                      &new_lineno, &wrapped))
     {
-      cpp_error (pfile, CPP_DL_ERROR,
-                "\"%s\" after #line is not a positive integer",
-                cpp_token_as_text (pfile, token));
+      if (token->type == CPP_EOF)
+       cpp_error (pfile, CPP_DL_ERROR, "unexpected end of file after #line");
+      else
+       cpp_error (pfile, CPP_DL_ERROR,
+                  "\"%s\" after #line is not a positive integer",
+                  cpp_token_as_text (pfile, token));
       return;
     }
 
-  if (CPP_PEDANTIC (pfile) && (new_lineno == 0 || new_lineno > cap))
+  if (CPP_PEDANTIC (pfile) && (new_lineno == 0 || new_lineno > cap || wrapped))
     cpp_error (pfile, CPP_DL_PEDWARN, "line number out of range");
+  else if (wrapped)
+    cpp_error (pfile, CPP_DL_WARNING, "line number out of range");
 
   token = cpp_get_token (pfile);
   if (token->type == CPP_STRING)
     {
       cpp_string s = { 0, 0 };
       if (cpp_interpret_string_notranslate (pfile, &token->val.str, 1,
-                                           &s, false))
+                                           &s, CPP_STRING))
        new_file = (const char *)s.text;
-      check_eol (pfile);
+      check_eol (pfile, true);
     }
   else if (token->type != CPP_EOF)
     {
@@ -890,8 +990,9 @@ do_line (cpp_reader *pfile)
     }
 
   skip_rest_of_line (pfile);
-  _cpp_do_file_change (pfile, LC_RENAME, new_file, new_lineno,
+  _cpp_do_file_change (pfile, LC_RENAME_VERBATIM, new_file, new_lineno,
                       map_sysp);
+  line_table->seen_line_directive = true;
 }
 
 /* Interpret the # 44 "file" [flags] notation, which has slightly
@@ -900,14 +1001,15 @@ do_line (cpp_reader *pfile)
 static void
 do_linemarker (cpp_reader *pfile)
 {
-  const struct line_maps *line_table = pfile->line_table;
-  const struct line_map *map = &line_table->maps[line_table->used - 1];
+  struct line_maps *line_table = pfile->line_table;
+  const line_map_ordinary *map = LINEMAPS_LAST_ORDINARY_MAP (line_table);
   const cpp_token *token;
-  const char *new_file = map->to_file;
-  unsigned long new_lineno;
-  unsigned int new_sysp = map->sysp;
-  enum lc_reason reason = LC_RENAME;
+  const char *new_file = ORDINARY_MAP_FILE_NAME (map);
+  linenum_type new_lineno;
+  unsigned int new_sysp = ORDINARY_MAP_IN_SYSTEM_HEADER_P (map);
+  enum lc_reason reason = LC_RENAME_VERBATIM;
   int flag;
+  bool wrapped;
 
   /* Back up so we can get the number again.  Putting this in
      _cpp_handle_directive risks two calls to _cpp_backup_tokens in
@@ -917,9 +1019,11 @@ do_linemarker (cpp_reader *pfile)
   /* #line commands expand macros.  */
   token = cpp_get_token (pfile);
   if (token->type != CPP_NUMBER
-      || strtoul_for_line (token->val.str.text, token->val.str.len,
-                          &new_lineno))
+      || strtolinenum (token->val.str.text, token->val.str.len,
+                      &new_lineno, &wrapped))
     {
+      /* Unlike #line, there does not seem to be a way to get an EOF
+        here.  So, it should be safe to always spell the token.  */
       cpp_error (pfile, CPP_DL_ERROR,
                 "\"%s\" after # is not a positive integer",
                 cpp_token_as_text (pfile, token));
@@ -931,7 +1035,7 @@ do_linemarker (cpp_reader *pfile)
     {
       cpp_string s = { 0, 0 };
       if (cpp_interpret_string_notranslate (pfile, &token->val.str,
-                                           1, &s, false))
+                                           1, &s, CPP_STRING))
        new_file = (const char *)s.text;
 
       new_sysp = 0;
@@ -957,7 +1061,7 @@ do_linemarker (cpp_reader *pfile)
        }
       pfile->buffer->sysp = new_sysp;
 
-      check_eol (pfile);
+      check_eol (pfile, false);
     }
   else if (token->type != CPP_EOF)
     {
@@ -967,7 +1071,33 @@ do_linemarker (cpp_reader *pfile)
     }
 
   skip_rest_of_line (pfile);
+
+  if (reason == LC_LEAVE)
+    {
+      /* Reread map since cpp_get_token can invalidate it with a
+        reallocation.  */
+      map = LINEMAPS_LAST_ORDINARY_MAP (line_table);
+      const line_map_ordinary *from
+       = linemap_included_from_linemap (line_table, map);
+      if (MAIN_FILE_P (map)
+         || (from
+             && filename_cmp (ORDINARY_MAP_FILE_NAME (from), new_file) != 0))
+       {
+         cpp_warning (pfile, CPP_W_NONE,
+                      "file \"%s\" linemarker ignored due to "
+                      "incorrect nesting", new_file);
+         return;
+       }
+    }
+  /* Compensate for the increment in linemap_add that occurs in
+     _cpp_do_file_change.  We're currently at the start of the line
+     *following* the #line directive.  A separate location_t for this
+     location makes no sense (until we do the LC_LEAVE), and
+     complicates LAST_SOURCE_LINE_LOCATION.  */
+  pfile->line_table->highest_location--;
+
   _cpp_do_file_change (pfile, reason, new_file, new_lineno, new_sysp);
+  line_table->seen_line_directive = true;
 }
 
 /* Arrange the file_change callback.  pfile->line has changed to
@@ -976,44 +1106,63 @@ do_linemarker (cpp_reader *pfile)
    and zero otherwise.  */
 void
 _cpp_do_file_change (cpp_reader *pfile, enum lc_reason reason,
-                    const char *to_file, unsigned int file_line,
+                    const char *to_file, linenum_type file_line,
                     unsigned int sysp)
 {
+  linemap_assert (reason != LC_ENTER_MACRO);
   const struct line_map *map = linemap_add (pfile->line_table, reason, sysp,
                                            to_file, file_line);
+  const line_map_ordinary *ord_map = NULL;
   if (map != NULL)
-    linemap_line_start (pfile->line_table, map->to_line, 127);
+    {
+      ord_map = linemap_check_ordinary (map);
+      linemap_line_start (pfile->line_table,
+                         ORDINARY_MAP_STARTING_LINE_NUMBER (ord_map),
+                         127);
+    }
 
   if (pfile->cb.file_change)
-    pfile->cb.file_change (pfile, map);
+    pfile->cb.file_change (pfile, ord_map);
 }
 
 /* Report a warning or error detected by the program we are
    processing.  Use the directive's tokens in the error message.  */
 static void
-do_diagnostic (cpp_reader *pfile, int code, int print_dir)
+do_diagnostic (cpp_reader *pfile, enum cpp_diagnostic_level code,
+              enum cpp_warning_reason reason, int print_dir)
 {
-  if (_cpp_begin_message (pfile, code, pfile->cur_token[-1].src_loc, 0))
-    {
-      if (print_dir)
-       fprintf (stderr, "#%s ", pfile->directive->name);
-      pfile->state.prevent_expansion++;
-      cpp_output_line (pfile, stderr);
-      pfile->state.prevent_expansion--;
-    }
+  const unsigned char *dir_name;
+  unsigned char *line;
+  location_t src_loc = pfile->cur_token[-1].src_loc;
+
+  if (print_dir)
+    dir_name = pfile->directive->name;
+  else
+    dir_name = NULL;
+  pfile->state.prevent_expansion++;
+  line = cpp_output_line_to_string (pfile, dir_name);
+  pfile->state.prevent_expansion--;
+
+  if (code == CPP_DL_WARNING_SYSHDR && reason)
+    cpp_warning_with_line_syshdr (pfile, reason, src_loc, 0, "%s", line);
+  else if (code == CPP_DL_WARNING && reason)
+    cpp_warning_with_line (pfile, reason, src_loc, 0, "%s", line);
+  else
+    cpp_error_with_line (pfile, code, src_loc, 0, "%s", line);
+  free (line);
 }
 
 static void
 do_error (cpp_reader *pfile)
 {
-  do_diagnostic (pfile, CPP_DL_ERROR, 1);
+  do_diagnostic (pfile, CPP_DL_ERROR, CPP_W_NONE, 1);
 }
 
 static void
 do_warning (cpp_reader *pfile)
 {
   /* We want #warning diagnostics to be emitted in system headers too.  */
-  do_diagnostic (pfile, CPP_DL_WARNING_SYSHDR, 1);
+  do_diagnostic (pfile, CPP_DL_WARNING_SYSHDR, CPP_W_WARNING_DIRECTIVE, 1);
 }
 
 /* Report program identification.  */
@@ -1028,7 +1177,7 @@ do_ident (cpp_reader *pfile)
   else if (pfile->cb.ident)
     pfile->cb.ident (pfile, pfile->directive_line, &str->val.str);
 
-  check_eol (pfile);
+  check_eol (pfile, false);
 }
 
 /* Lookup a PRAGMA name in a singly-linked CHAIN.  Returns the
@@ -1072,7 +1221,7 @@ register_pragma_1 (cpp_reader *pfile, const char *space, const char *name,
 
   if (space)
     {
-      node = cpp_lookup (pfile, U space, strlen (space));
+      node = cpp_lookup (pfile, UC space, strlen (space));
       entry = lookup_pragma_entry (*chain, node);
       if (!entry)
        {
@@ -1101,7 +1250,7 @@ register_pragma_1 (cpp_reader *pfile, const char *space, const char *name,
     }
 
   /* Check for duplicates.  */
-  node = cpp_lookup (pfile, U name, strlen (name));
+  node = cpp_lookup (pfile, UC name, strlen (name));
   entry = lookup_pragma_entry (*chain, node);
   if (entry == NULL)
     {
@@ -1186,12 +1335,16 @@ _cpp_init_internal_pragmas (cpp_reader *pfile)
 {
   /* Pragmas in the global namespace.  */
   register_pragma_internal (pfile, 0, "once", do_pragma_once);
+  register_pragma_internal (pfile, 0, "push_macro", do_pragma_push_macro);
+  register_pragma_internal (pfile, 0, "pop_macro", do_pragma_pop_macro);
 
   /* New GCC-specific pragmas should be put in the GCC namespace.  */
   register_pragma_internal (pfile, "GCC", "poison", do_pragma_poison);
   register_pragma_internal (pfile, "GCC", "system_header",
                            do_pragma_system_header);
   register_pragma_internal (pfile, "GCC", "dependency", do_pragma_dependency);
+  register_pragma_internal (pfile, "GCC", "warning", do_pragma_warning);
+  register_pragma_internal (pfile, "GCC", "error", do_pragma_error);
 }
 
 /* Return the number of registered pragmas in PE.  */
@@ -1249,7 +1402,7 @@ restore_registered_pragmas (cpp_reader *pfile, struct pragma_entry *pe,
     {
       if (pe->is_nspace)
        sd = restore_registered_pragmas (pfile, pe->u.space, sd);
-      pe->pragma = cpp_lookup (pfile, U *sd, strlen (*sd));
+      pe->pragma = cpp_lookup (pfile, UC *sd, strlen (*sd));
       free (*sd);
       sd++;
     }
@@ -1276,25 +1429,28 @@ static void
 do_pragma (cpp_reader *pfile)
 {
   const struct pragma_entry *p = NULL;
-  const cpp_token *token, *pragma_token = pfile->cur_token;
+  const cpp_token *token, *pragma_token;
+  location_t pragma_token_virt_loc = 0;
   cpp_token ns_token;
   unsigned int count = 1;
 
   pfile->state.prevent_expansion++;
 
-  token = cpp_get_token (pfile);
+  pragma_token = token = cpp_get_token_with_location (pfile,
+                                                     &pragma_token_virt_loc);
   ns_token = *token;
   if (token->type == CPP_NAME)
     {
-      p = lookup_pragma_entry (pfile->pragmas, token->val.node);
+      p = lookup_pragma_entry (pfile->pragmas, token->val.node.node);
       if (p && p->is_nspace)
        {
          bool allow_name_expansion = p->allow_expansion;
          if (allow_name_expansion)
            pfile->state.prevent_expansion--;
+
          token = cpp_get_token (pfile);
          if (token->type == CPP_NAME)
-           p = lookup_pragma_entry (p->u.space, token->val.node);
+           p = lookup_pragma_entry (p->u.space, token->val.node.node);
          else
            p = NULL;
          if (allow_name_expansion)
@@ -1307,7 +1463,7 @@ do_pragma (cpp_reader *pfile)
     {
       if (p->is_deferred)
        {
-         pfile->directive_result.src_loc = pragma_token->src_loc;
+         pfile->directive_result.src_loc = pragma_token_virt_loc;
          pfile->directive_result.type = CPP_PRAGMA;
          pfile->directive_result.flags = pragma_token->flags;
          pfile->directive_result.val.pragma = p->u.ident;
@@ -1361,10 +1517,120 @@ do_pragma_once (cpp_reader *pfile)
   if (cpp_in_primary_file (pfile))
     cpp_error (pfile, CPP_DL_WARNING, "#pragma once in main file");
 
-  check_eol (pfile);
+  check_eol (pfile, false);
   _cpp_mark_file_once_only (pfile, pfile->buffer->file);
 }
 
+/* Handle #pragma push_macro(STRING).  */
+static void
+do_pragma_push_macro (cpp_reader *pfile)
+{
+  cpp_hashnode *node;
+  size_t defnlen;
+  const uchar *defn = NULL;
+  char *macroname, *dest;
+  const char *limit, *src;
+  const cpp_token *txt;
+  struct def_pragma_macro *c;
+
+  txt = get__Pragma_string (pfile);
+  if (!txt)
+    {
+      location_t src_loc = pfile->cur_token[-1].src_loc;
+      cpp_error_with_line (pfile, CPP_DL_ERROR, src_loc, 0,
+                "invalid #pragma push_macro directive");
+      check_eol (pfile, false);
+      skip_rest_of_line (pfile);
+      return;
+    }
+  dest = macroname = (char *) alloca (txt->val.str.len + 2);
+  src = (const char *) (txt->val.str.text + 1 + (txt->val.str.text[0] == 'L'));
+  limit = (const char *) (txt->val.str.text + txt->val.str.len - 1);
+  while (src < limit)
+    {
+      /* We know there is a character following the backslash.  */
+      if (*src == '\\' && (src[1] == '\\' || src[1] == '"'))
+       src++;
+      *dest++ = *src++;
+    }
+  *dest = 0;
+  check_eol (pfile, false);
+  skip_rest_of_line (pfile);
+  c = XNEW (struct def_pragma_macro);
+  memset (c, 0, sizeof (struct def_pragma_macro));
+  c->name = XNEWVAR (char, strlen (macroname) + 1);
+  strcpy (c->name, macroname);
+  c->next = pfile->pushed_macros;
+  node = _cpp_lex_identifier (pfile, c->name);
+  if (node->type == NT_VOID)
+    c->is_undef = 1;
+  else
+    {
+      defn = cpp_macro_definition (pfile, node);
+      defnlen = ustrlen (defn);
+      c->definition = XNEWVEC (uchar, defnlen + 2);
+      c->definition[defnlen] = '\n';
+      c->definition[defnlen + 1] = 0;
+      c->line = node->value.macro->line;
+      c->syshdr = node->value.macro->syshdr;
+      c->used = node->value.macro->used;
+      memcpy (c->definition, defn, defnlen);
+    }
+
+  pfile->pushed_macros = c;
+}
+
+/* Handle #pragma pop_macro(STRING).  */
+static void
+do_pragma_pop_macro (cpp_reader *pfile)
+{
+  char *macroname, *dest;
+  const char *limit, *src;
+  const cpp_token *txt;
+  struct def_pragma_macro *l = NULL, *c = pfile->pushed_macros;
+  txt = get__Pragma_string (pfile);
+  if (!txt)
+    {
+      location_t src_loc = pfile->cur_token[-1].src_loc;
+      cpp_error_with_line (pfile, CPP_DL_ERROR, src_loc, 0,
+                "invalid #pragma pop_macro directive");
+      check_eol (pfile, false);
+      skip_rest_of_line (pfile);
+      return;
+    }
+  dest = macroname = (char *) alloca (txt->val.str.len + 2);
+  src = (const char *) (txt->val.str.text + 1 + (txt->val.str.text[0] == 'L'));
+  limit = (const char *) (txt->val.str.text + txt->val.str.len - 1);
+  while (src < limit)
+    {
+      /* We know there is a character following the backslash.  */
+      if (*src == '\\' && (src[1] == '\\' || src[1] == '"'))
+       src++;
+      *dest++ = *src++;
+    }
+  *dest = 0;
+  check_eol (pfile, false);
+  skip_rest_of_line (pfile);
+
+  while (c != NULL)
+    {
+      if (!strcmp (c->name, macroname))
+       {
+         if (!l)
+           pfile->pushed_macros = c->next;
+         else
+           l->next = c->next;
+         cpp_pop_definition (pfile, c);
+         free (c->definition);
+         free (c->name);
+         free (c);
+         break;
+       }
+      l = c;
+      c = c->next;
+    }
+}
+
 /* Handle #pragma GCC poison, to poison one or more identifiers so
    that the lexer produces a hard error for each subsequent usage.  */
 static void
@@ -1386,11 +1652,11 @@ do_pragma_poison (cpp_reader *pfile)
          break;
        }
 
-      hp = tok->val.node;
+      hp = tok->val.node.node;
       if (hp->flags & NODE_POISONED)
        continue;
 
-      if (hp->type == NT_MACRO)
+      if (cpp_macro_p (hp))
        cpp_error (pfile, CPP_DL_WARNING, "poisoning existing macro \"%s\"",
                   NODE_NAME (hp));
       _cpp_free_definition (hp);
@@ -1413,7 +1679,7 @@ do_pragma_system_header (cpp_reader *pfile)
               "#pragma system_header ignored outside include file");
   else
     {
-      check_eol (pfile);
+      check_eol (pfile, false);
       skip_rest_of_line (pfile);
       cpp_make_system_header (pfile, 1, 0);
     }
@@ -1427,8 +1693,9 @@ do_pragma_dependency (cpp_reader *pfile)
 {
   const char *fname;
   int angle_brackets, ordering;
+  location_t location;
 
-  fname = parse_include (pfile, &angle_brackets, NULL);
+  fname = parse_include (pfile, &angle_brackets, NULL, &location);
   if (!fname)
     return;
 
@@ -1442,13 +1709,49 @@ do_pragma_dependency (cpp_reader *pfile)
       if (cpp_get_token (pfile)->type != CPP_EOF)
        {
          _cpp_backup_tokens (pfile, 1);
-         do_diagnostic (pfile, CPP_DL_WARNING, 0);
+         do_diagnostic (pfile, CPP_DL_WARNING, CPP_W_NONE, 0);
        }
     }
 
   free ((void *) fname);
 }
 
+/* Issue a diagnostic with the message taken from the pragma.  If
+   ERROR is true, the diagnostic is a warning, otherwise, it is an
+   error.  */
+static void
+do_pragma_warning_or_error (cpp_reader *pfile, bool error)
+{
+  const cpp_token *tok = _cpp_lex_token (pfile);
+  cpp_string str;
+  if (tok->type != CPP_STRING
+      || !cpp_interpret_string_notranslate (pfile, &tok->val.str, 1, &str,
+                                           CPP_STRING)
+      || str.len == 0)
+    {
+      cpp_error (pfile, CPP_DL_ERROR, "invalid \"#pragma GCC %s\" directive",
+                error ? "error" : "warning");
+      return;
+    }
+  cpp_error (pfile, error ? CPP_DL_ERROR : CPP_DL_WARNING,
+            "%s", str.text);
+  free ((void *)str.text);
+}
+
+/* Issue a warning diagnostic.  */
+static void
+do_pragma_warning (cpp_reader *pfile)
+{
+  do_pragma_warning_or_error (pfile, false);
+}
+
+/* Issue an error diagnostic.  */
+static void
+do_pragma_error (cpp_reader *pfile)
+{
+  do_pragma_warning_or_error (pfile, true);
+}
+
 /* Get a token but skip padding.  */
 static const cpp_token *
 get_token_no_padding (cpp_reader *pfile)
@@ -1467,15 +1770,26 @@ static const cpp_token *
 get__Pragma_string (cpp_reader *pfile)
 {
   const cpp_token *string;
+  const cpp_token *paren;
 
-  if (get_token_no_padding (pfile)->type != CPP_OPEN_PAREN)
+  paren = get_token_no_padding (pfile);
+  if (paren->type == CPP_EOF)
+    _cpp_backup_tokens (pfile, 1);
+  if (paren->type != CPP_OPEN_PAREN)
     return NULL;
 
   string = get_token_no_padding (pfile);
-  if (string->type != CPP_STRING && string->type != CPP_WSTRING)
+  if (string->type == CPP_EOF)
+    _cpp_backup_tokens (pfile, 1);
+  if (string->type != CPP_STRING && string->type != CPP_WSTRING
+      && string->type != CPP_STRING32 && string->type != CPP_STRING16
+      && string->type != CPP_UTF8STRING)
     return NULL;
 
-  if (get_token_no_padding (pfile)->type != CPP_CLOSE_PAREN)
+  paren = get_token_no_padding (pfile);
+  if (paren->type == CPP_EOF)
+    _cpp_backup_tokens (pfile, 1);
+  if (paren->type != CPP_CLOSE_PAREN)
     return NULL;
 
   return string;
@@ -1484,7 +1798,8 @@ get__Pragma_string (cpp_reader *pfile)
 /* Destringize IN into a temporary buffer, by removing the first \ of
    \" and \\ sequences, and process the result as a #pragma directive.  */
 static void
-destringize_and_run (cpp_reader *pfile, const cpp_string *in)
+destringize_and_run (cpp_reader *pfile, const cpp_string *in,
+                    location_t expansion_loc)
 {
   const unsigned char *src, *limit;
   char *dest, *result;
@@ -1493,6 +1808,7 @@ destringize_and_run (cpp_reader *pfile, const cpp_string *in)
   tokenrun *saved_cur_run;
   cpp_token *toks;
   int count;
+  const struct directive *save_directive;
 
   dest = result = (char *) alloca (in->len - 1);
   src = in->text + 1 + (in->text[0] == 'L');
@@ -1518,10 +1834,7 @@ destringize_and_run (cpp_reader *pfile, const cpp_string *in)
   saved_cur_token = pfile->cur_token;
   saved_cur_run = pfile->cur_run;
 
-  pfile->context = XNEW (cpp_context);
-  pfile->context->macro = 0;
-  pfile->context->prev = 0;
-  pfile->context->next = 0;
+  pfile->context = XCNEW (cpp_context);
 
   /* Inline run_directive, since we need to delay the _cpp_pop_buffer
      until we've read all of the tokens that we want.  */
@@ -1533,8 +1846,11 @@ destringize_and_run (cpp_reader *pfile, const cpp_string *in)
 
   start_directive (pfile);
   _cpp_clean_line (pfile);
+  save_directive = pfile->directive;
+  pfile->directive = &dtable[T_PRAGMA];
   do_pragma (pfile);
   end_directive (pfile, 1);
+  pfile->directive = save_directive;
 
   /* We always insert at least one token, the directive result.  It'll
      either be a CPP_PADDING or a CPP_PRAGMA.  In the later case, we 
@@ -1563,6 +1879,12 @@ destringize_and_run (cpp_reader *pfile, const cpp_string *in)
              toks = XRESIZEVEC (cpp_token, toks, maxcount);
            }
          toks[count] = *cpp_get_token (pfile);
+         /* _Pragma is a builtin, so we're not within a macro-map, and so
+            the token locations are set to bogus ordinary locations
+            near to, but after that of the "_Pragma".
+            Paper over this by setting them equal to the location of the
+            _Pragma itself (PR preprocessor/69126).  */
+         toks[count].src_loc = expansion_loc;
          /* Macros have been already expanded by cpp_get_token
             if the pragma allowed expansion.  */
          toks[count++].flags |= NO_EXPAND;
@@ -1595,18 +1917,21 @@ destringize_and_run (cpp_reader *pfile, const cpp_string *in)
   _cpp_push_token_context (pfile, NULL, toks, count);
 }
 
-/* Handle the _Pragma operator.  */
-void
-_cpp_do__Pragma (cpp_reader *pfile)
+/* Handle the _Pragma operator.  Return 0 on error, 1 if ok.  */
+int
+_cpp_do__Pragma (cpp_reader *pfile, location_t expansion_loc)
 {
   const cpp_token *string = get__Pragma_string (pfile);
   pfile->directive_result.type = CPP_PADDING;
 
   if (string)
-    destringize_and_run (pfile, &string->val.str);
-  else
-    cpp_error (pfile, CPP_DL_ERROR,
-              "_Pragma takes a parenthesized string literal");
+    {
+      destringize_and_run (pfile, &string->val.str, expansion_loc);
+      return 1;
+    }
+  cpp_error (pfile, CPP_DL_ERROR,
+            "_Pragma takes a parenthesized string literal");
+  return 0;
 }
 
 /* Handle #ifdef.  */
@@ -1617,13 +1942,20 @@ do_ifdef (cpp_reader *pfile)
 
   if (! pfile->state.skipping)
     {
-      const cpp_hashnode *node = lex_macro_node (pfile, false);
+      cpp_hashnode *node = lex_macro_node (pfile, false);
 
       if (node)
        {
-         skip = node->type != NT_MACRO;
+         /* Do not treat conditional macros as being defined.  This is due to
+            the powerpc and spu ports using conditional macros for 'vector',
+            'bool', and 'pixel' to act as conditional keywords.  This messes
+            up tests like #ifndef bool.  */
+         skip = !cpp_macro_p (node) || (node->flags & NODE_CONDITIONAL);
          _cpp_mark_macro_used (node);
-         check_eol (pfile);
+         _cpp_maybe_notify_macro_use (pfile, node);
+         if (pfile->cb.used)
+           pfile->cb.used (pfile, pfile->directive_line, node);
+         check_eol (pfile, false);
        }
     }
 
@@ -1635,7 +1967,7 @@ static void
 do_ifndef (cpp_reader *pfile)
 {
   int skip = 1;
-  const cpp_hashnode *node = 0;
+  cpp_hashnode *node = 0;
 
   if (! pfile->state.skipping)
     {
@@ -1643,9 +1975,17 @@ do_ifndef (cpp_reader *pfile)
 
       if (node)
        {
-         skip = node->type == NT_MACRO;
+         /* Do not treat conditional macros as being defined.  This is due to
+            the powerpc and spu ports using conditional macros for 'vector',
+            'bool', and 'pixel' to act as conditional keywords.  This messes
+            up tests like #ifndef bool.  */
+         skip = (cpp_macro_p (node)
+                 && !(node->flags & NODE_CONDITIONAL));
          _cpp_mark_macro_used (node);
-         check_eol (pfile);
+         _cpp_maybe_notify_macro_use (pfile, node);
+         if (pfile->cb.used)
+           pfile->cb.used (pfile, pfile->directive_line, node);
+         check_eol (pfile, false);
        }
     }
 
@@ -1663,7 +2003,7 @@ do_if (cpp_reader *pfile)
   int skip = 1;
 
   if (! pfile->state.skipping)
-    skip = _cpp_parse_expr (pfile) == false;
+    skip = _cpp_parse_expr (pfile, true) == false;
 
   push_conditional (pfile, skip, T_IF, pfile->mi_ind_cmacro);
 }
@@ -1698,7 +2038,7 @@ do_else (cpp_reader *pfile)
 
       /* Only check EOL if was not originally skipping.  */
       if (!ifs->was_skipping && CPP_OPTION (pfile, warn_endif_labels))
-       check_eol (pfile);
+       check_eol_endif_labels (pfile);
     }
 }
 
@@ -1722,14 +2062,15 @@ do_elif (cpp_reader *pfile)
        }
       ifs->type = T_ELIF;
 
-      /* Only evaluate this if we aren't skipping elses.  During
-        evaluation, set skipping to false to get lexer warnings.  */
+      /* See DR#412: "Only the first group whose control condition
+        evaluates to true (nonzero) is processed; any following groups
+        are skipped and their controlling directives are processed as
+        if they were in a group that is skipped."  */
       if (ifs->skip_elses)
        pfile->state.skipping = 1;
       else
        {
-         pfile->state.skipping = 0;
-         pfile->state.skipping = ! _cpp_parse_expr (pfile);
+         pfile->state.skipping = ! _cpp_parse_expr (pfile, false);
          ifs->skip_elses = ! pfile->state.skipping;
        }
 
@@ -1751,7 +2092,7 @@ do_endif (cpp_reader *pfile)
     {
       /* Only check EOL if was not originally skipping.  */
       if (!ifs->was_skipping && CPP_OPTION (pfile, warn_endif_labels))
-       check_eol (pfile);
+       check_eol_endif_labels (pfile);
 
       /* If potential control macro, we go back outside again.  */
       if (ifs->next == 0 && ifs->mi_cmacro)
@@ -1796,17 +2137,15 @@ push_conditional (cpp_reader *pfile, int skip, int type,
 /* Read the tokens of the answer into the macro pool, in a directive
    of type TYPE.  Only commit the memory if we intend it as permanent
    storage, i.e. the #assert case.  Returns 0 on success, and sets
-   ANSWERP to point to the answer.  */
-static int
-parse_answer (cpp_reader *pfile, struct answer **answerp, int type)
+   ANSWERP to point to the answer.  PRED_LOC is the location of the
+   predicate.  */
+static bool
+parse_answer (cpp_reader *pfile, int type, location_t pred_loc,
+             cpp_macro **answer_ptr)
 {
-  const cpp_token *paren;
-  struct answer *answer;
-  unsigned int acount;
-
   /* In a conditional, it is legal to not have an open paren.  We
      should save the following token in this case.  */
-  paren = cpp_get_token (pfile);
+  const cpp_token *paren = cpp_get_token (pfile);
 
   /* If not a paren, see if we're OK.  */
   if (paren->type != CPP_OPEN_PAREN)
@@ -1816,22 +2155,26 @@ parse_answer (cpp_reader *pfile, struct answer **answerp, int type)
       if (type == T_IF)
        {
          _cpp_backup_tokens (pfile, 1);
-         return 0;
+         return true;
        }
 
       /* #unassert with no answer is valid - it removes all answers.  */
       if (type == T_UNASSERT && paren->type == CPP_EOF)
-       return 0;
+       return true;
 
-      cpp_error (pfile, CPP_DL_ERROR, "missing '(' after predicate");
-      return 1;
+      cpp_error_with_line (pfile, CPP_DL_ERROR, pred_loc, 0,
+                          "missing '(' after predicate");
+      return false;
     }
 
-  for (acount = 0;; acount++)
+  cpp_macro *answer = _cpp_new_macro (pfile, cmk_assert,
+                                     _cpp_reserve_room (pfile, 0,
+                                                        sizeof (cpp_macro)));
+  answer->parm.next = NULL;
+  unsigned count = 0;
+  for (;;)
     {
-      size_t room_needed;
       const cpp_token *token = cpp_get_token (pfile);
-      cpp_token *dest;
 
       if (token->type == CPP_CLOSE_PAREN)
        break;
@@ -1839,86 +2182,84 @@ parse_answer (cpp_reader *pfile, struct answer **answerp, int type)
       if (token->type == CPP_EOF)
        {
          cpp_error (pfile, CPP_DL_ERROR, "missing ')' to complete answer");
-         return 1;
+         return false;
        }
 
-      /* struct answer includes the space for one token.  */
-      room_needed = (sizeof (struct answer) + acount * sizeof (cpp_token));
-
-      if (BUFF_ROOM (pfile->a_buff) < room_needed)
-       _cpp_extend_buff (pfile, &pfile->a_buff, sizeof (struct answer));
-
-      dest = &((struct answer *) BUFF_FRONT (pfile->a_buff))->first[acount];
-      *dest = *token;
-
-      /* Drop whitespace at start, for answer equivalence purposes.  */
-      if (acount == 0)
-       dest->flags &= ~PREV_WHITE;
+      answer = (cpp_macro *)_cpp_reserve_room
+       (pfile, sizeof (cpp_macro) + count * sizeof (cpp_token),
+        sizeof (cpp_token));
+      answer->exp.tokens[count++] = *token;
     }
 
-  if (acount == 0)
+  if (!count)
     {
       cpp_error (pfile, CPP_DL_ERROR, "predicate's answer is empty");
-      return 1;
+      return false;
     }
 
-  answer = (struct answer *) BUFF_FRONT (pfile->a_buff);
-  answer->count = acount;
-  answer->next = NULL;
-  *answerp = answer;
+  /* Drop whitespace at start, for answer equivalence purposes.  */
+  answer->exp.tokens[0].flags &= ~PREV_WHITE;
 
-  return 0;
+  answer->count = count;
+  *answer_ptr = answer;
+
+  return true;
 }
 
 /* Parses an assertion directive of type TYPE, returning a pointer to
-   the hash node of the predicate, or 0 on error.  If an answer was
-   supplied, it is placed in ANSWERP, otherwise it is set to 0.  */
+   the hash node of the predicate, or 0 on error.  The node is
+   guaranteed to be disjoint from the macro namespace, so can only
+   have type 'NT_VOID'.  If an answer was supplied, it is placed in
+   *ANSWER_PTR, which is otherwise set to 0.  */
 static cpp_hashnode *
-parse_assertion (cpp_reader *pfile, struct answer **answerp, int type)
+parse_assertion (cpp_reader *pfile, int type, cpp_macro **answer_ptr)
 {
   cpp_hashnode *result = 0;
-  const cpp_token *predicate;
 
   /* We don't expand predicates or answers.  */
   pfile->state.prevent_expansion++;
 
-  *answerp = 0;
-  predicate = cpp_get_token (pfile);
+  *answer_ptr = NULL;
+
+  const cpp_token *predicate = cpp_get_token (pfile);
   if (predicate->type == CPP_EOF)
     cpp_error (pfile, CPP_DL_ERROR, "assertion without predicate");
   else if (predicate->type != CPP_NAME)
-    cpp_error (pfile, CPP_DL_ERROR, "predicate must be an identifier");
-  else if (parse_answer (pfile, answerp, type) == 0)
+    cpp_error_with_line (pfile, CPP_DL_ERROR, predicate->src_loc, 0,
+                        "predicate must be an identifier");
+  else if (parse_answer (pfile, type, predicate->src_loc, answer_ptr))
     {
-      unsigned int len = NODE_LEN (predicate->val.node);
+      unsigned int len = NODE_LEN (predicate->val.node.node);
       unsigned char *sym = (unsigned char *) alloca (len + 1);
 
       /* Prefix '#' to get it out of macro namespace.  */
       sym[0] = '#';
-      memcpy (sym + 1, NODE_NAME (predicate->val.node), len);
+      memcpy (sym + 1, NODE_NAME (predicate->val.node.node), len);
       result = cpp_lookup (pfile, sym, len + 1);
     }
 
   pfile->state.prevent_expansion--;
+
   return result;
 }
 
 /* Returns a pointer to the pointer to CANDIDATE in the answer chain,
    or a pointer to NULL if the answer is not in the chain.  */
-static struct answer **
-find_answer (cpp_hashnode *node, const struct answer *candidate)
+static cpp_macro **
+find_answer (cpp_hashnode *node, const cpp_macro *candidate)
 {
   unsigned int i;
-  struct answer **result;
+  cpp_macro **result = NULL;
 
-  for (result = &node->value.answers; *result; result = &(*result)->next)
+  for (result = &node->value.answers; *result; result = &(*result)->parm.next)
     {
-      struct answer *answer = *result;
+      cpp_macro *answer = *result;
 
       if (answer->count == candidate->count)
        {
          for (i = 0; i < answer->count; i++)
-           if (! _cpp_equiv_tokens (&answer->first[i], &candidate->first[i]))
+           if (!_cpp_equiv_tokens (&answer->exp.tokens[i],
+                                   &candidate->exp.tokens[i]))
              break;
 
          if (i == answer->count)
@@ -1935,18 +2276,18 @@ find_answer (cpp_hashnode *node, const struct answer *candidate)
 int
 _cpp_test_assertion (cpp_reader *pfile, unsigned int *value)
 {
-  struct answer *answer;
-  cpp_hashnode *node;
-
-  node = parse_assertion (pfile, &answer, T_IF);
+  cpp_macro *answer;
+  cpp_hashnode *node = parse_assertion (pfile, T_IF, &answer);
 
   /* For recovery, an erroneous assertion expression is handled as a
      failing assertion.  */
   *value = 0;
 
   if (node)
-    *value = (node->type == NT_ASSERTION &&
-             (answer == 0 || *find_answer (node, answer) != 0));
+    {
+      if (node->value.answers)
+       *value = !answer || *find_answer (node, answer);
+    }
   else if (pfile->cur_token[-1].type == CPP_EOF)
     _cpp_backup_tokens (pfile, 1);
 
@@ -1958,44 +2299,30 @@ _cpp_test_assertion (cpp_reader *pfile, unsigned int *value)
 static void
 do_assert (cpp_reader *pfile)
 {
-  struct answer *new_answer;
-  cpp_hashnode *node;
+  cpp_macro *answer;
+  cpp_hashnode *node = parse_assertion (pfile, T_ASSERT, &answer);
 
-  node = parse_assertion (pfile, &new_answer, T_ASSERT);
   if (node)
     {
-      size_t answer_size;
-
       /* Place the new answer in the answer list.  First check there
          is not a duplicate.  */
-      new_answer->next = 0;
-      if (node->type == NT_ASSERTION)
+      if (*find_answer (node, answer))
        {
-         if (*find_answer (node, new_answer))
-           {
-             cpp_error (pfile, CPP_DL_WARNING, "\"%s\" re-asserted",
-                        NODE_NAME (node) + 1);
-             return;
-           }
-         new_answer->next = node->value.answers;
+         cpp_error (pfile, CPP_DL_WARNING, "\"%s\" re-asserted",
+                    NODE_NAME (node) + 1);
+         return;
        }
 
-      answer_size = sizeof (struct answer) + ((new_answer->count - 1)
-                                             * sizeof (cpp_token));
-      /* Commit or allocate storage for the object.  */
-      if (pfile->hash_table->alloc_subobject)
-       {
-         struct answer *temp_answer = new_answer;
-         new_answer = (struct answer *) pfile->hash_table->alloc_subobject
-            (answer_size);
-         memcpy (new_answer, temp_answer, answer_size);
-       }
-      else
-       BUFF_FRONT (pfile->a_buff) += answer_size;
+      /* Commit or allocate storage for the answer.  */
+      answer = (cpp_macro *)_cpp_commit_buff
+       (pfile, sizeof (cpp_macro) - sizeof (cpp_token)
+        + sizeof (cpp_token) * answer->count);
 
-      node->type = NT_ASSERTION;
-      node->value.answers = new_answer;
-      check_eol (pfile);
+      /* Chain into the list.  */
+      answer->parm.next = node->value.answers;
+      node->value.answers = answer;
+
+      check_eol (pfile, false);
     }
 }
 
@@ -2003,27 +2330,21 @@ do_assert (cpp_reader *pfile)
 static void
 do_unassert (cpp_reader *pfile)
 {
-  cpp_hashnode *node;
-  struct answer *answer;
+  cpp_macro *answer;
+  cpp_hashnode *node = parse_assertion (pfile, T_UNASSERT, &answer);
 
-  node = parse_assertion (pfile, &answer, T_UNASSERT);
   /* It isn't an error to #unassert something that isn't asserted.  */
-  if (node && node->type == NT_ASSERTION)
+  if (node)
     {
       if (answer)
        {
-         struct answer **p = find_answer (node, answer), *temp;
+         cpp_macro **p = find_answer (node, answer);
 
-         /* Remove the answer from the list.  */
-         temp = *p;
-         if (temp)
-           *p = temp->next;
+         /* Remove the assert from the list.  */
+         if (cpp_macro *temp = *p)
+           *p = temp->parm.next;
 
-         /* Did we free the last answer?  */
-         if (node->value.answers == 0)
-           node->type = NT_VOID;
-
-         check_eol (pfile);
+         check_eol (pfile, false);
        }
       else
        _cpp_free_definition (node);
@@ -2041,7 +2362,8 @@ do_unassert (cpp_reader *pfile)
 void
 cpp_define (cpp_reader *pfile, const char *str)
 {
-  char *buf, *p;
+  char *buf;
+  const char *p;
   size_t count;
 
   /* Copy the entire option so we can modify it.
@@ -2065,6 +2387,26 @@ cpp_define (cpp_reader *pfile, const char *str)
   run_directive (pfile, T_DEFINE, buf, count);
 }
 
+
+/* Use to build macros to be run through cpp_define() as
+   described above.
+   Example: cpp_define_formatted (pfile, "MACRO=%d", value);  */
+
+void
+cpp_define_formatted (cpp_reader *pfile, const char *fmt, ...)
+{
+  char *ptr;
+
+  va_list ap;
+  va_start (ap, fmt);
+  ptr = xvasprintf (fmt, ap);
+  va_end (ap);
+
+  cpp_define (pfile, ptr);
+  free (ptr);
+}
+
+
 /* Slight variant of the above for use by initialize_builtins.  */
 void
 _cpp_define_builtin (cpp_reader *pfile, const char *str)
@@ -2087,63 +2429,55 @@ cpp_undef (cpp_reader *pfile, const char *macro)
   run_directive (pfile, T_UNDEF, buf, len);
 }
 
-/* Like lex_macro_node, but read the input from STR.  */
-static cpp_hashnode *
-lex_macro_node_from_str (cpp_reader *pfile, const char *str)
-{
-  size_t len = strlen (str);
-  uchar *buf = (uchar *) alloca (len + 1);
-  cpp_hashnode *node;
-
-  memcpy (buf, str, len);
-  buf[len] = '\n';
-  cpp_push_buffer (pfile, buf, len, true);
-  node = lex_macro_node (pfile, true);
-  _cpp_pop_buffer (pfile);
-
-  return node;
-}
-
-/* If STR is a defined macro, return its definition node, else return NULL.  */
-cpp_macro *
-cpp_push_definition (cpp_reader *pfile, const char *str)
-{
-  cpp_hashnode *node = lex_macro_node_from_str (pfile, str);
-  if (node && node->type == NT_MACRO)
-    return node->value.macro;
-  else
-    return NULL;
-}
-
-/* Replace a previous definition DFN of the macro STR.  If DFN is NULL,
-   then the macro should be undefined.  */
-void
-cpp_pop_definition (cpp_reader *pfile, const char *str, cpp_macro *dfn)
+/* Replace a previous definition DEF of the macro STR.  If DEF is NULL,
+   or first element is zero, then the macro should be undefined.  */
+static void
+cpp_pop_definition (cpp_reader *pfile, struct def_pragma_macro *c)
 {
-  cpp_hashnode *node = lex_macro_node_from_str (pfile, str);
+  cpp_hashnode *node = _cpp_lex_identifier (pfile, c->name);
   if (node == NULL)
     return;
 
-  if (node->type == NT_MACRO)
+  if (pfile->cb.before_define)
+    pfile->cb.before_define (pfile);
+
+  if (cpp_macro_p (node))
     {
       if (pfile->cb.undef)
        pfile->cb.undef (pfile, pfile->directive_line, node);
       if (CPP_OPTION (pfile, warn_unused_macros))
        _cpp_warn_if_unused_macro (pfile, node, NULL);
+      _cpp_free_definition (node);
     }
-  if (node->type != NT_VOID)
-    _cpp_free_definition (node);
 
-  if (dfn)
-    {
-      node->type = NT_MACRO;
-      node->value.macro = dfn;
-      if (! ustrncmp (NODE_NAME (node), DSC ("__STDC_")))
-       node->flags |= NODE_WARN;
+  if (c->is_undef)
+    return;
 
-      if (pfile->cb.define)
-       pfile->cb.define (pfile, pfile->directive_line, node);
-    }
+  {
+    size_t namelen;
+    const uchar *dn;
+    cpp_hashnode *h = NULL;
+    cpp_buffer *nbuf;
+
+    namelen = ustrcspn (c->definition, "( \n");
+    h = cpp_lookup (pfile, c->definition, namelen);
+    dn = c->definition + namelen;
+
+    nbuf = cpp_push_buffer (pfile, dn, ustrchr (dn, '\n') - dn, true);
+    if (nbuf != NULL)
+      {
+       _cpp_clean_line (pfile);
+       nbuf->sysp = 1;
+       if (!_cpp_create_definition (pfile, h))
+         abort ();
+       _cpp_pop_buffer (pfile);
+      }
+    else
+      abort ();
+    h->value.macro->line = c->line;
+    h->value.macro->syshdr = c->syshdr;
+    h->value.macro->used = c->used;
+  }
 }
 
 /* Process the string STR as if it appeared as the body of a #assert.  */
@@ -2183,13 +2517,6 @@ handle_assertion (cpp_reader *pfile, const char *str, int type)
   run_directive (pfile, type, str, count);
 }
 
-/* The number of errors for a given reader.  */
-unsigned int
-cpp_errors (cpp_reader *pfile)
-{
-  return pfile->errors;
-}
-
 /* The options structure.  */
 cpp_options *
 cpp_get_options (cpp_reader *pfile)
@@ -2251,6 +2578,7 @@ _cpp_pop_buffer (cpp_reader *pfile)
   cpp_buffer *buffer = pfile->buffer;
   struct _cpp_file *inc = buffer->file;
   struct if_stack *ifs;
+  const unsigned char *to_free;
 
   /* Walk back up the conditional stack till we reach its level at
      entry to this file, issuing error messages.  */
@@ -2264,6 +2592,7 @@ _cpp_pop_buffer (cpp_reader *pfile)
   /* _cpp_do_file_change expects pfile->buffer to be the new one.  */
   pfile->buffer = buffer->prev;
 
+  to_free = buffer->to_free;
   free (buffer->notes);
 
   /* Free the buffer object now; we may want to push a new buffer
@@ -2272,10 +2601,12 @@ _cpp_pop_buffer (cpp_reader *pfile)
 
   if (inc)
     {
-      _cpp_pop_file_buffer (pfile, inc);
+      _cpp_pop_file_buffer (pfile, inc, to_free);
 
       _cpp_do_file_change (pfile, LC_LEAVE, 0, 0, 0);
     }
+  else if (to_free)
+    free ((void *)to_free);
 }
 
 /* Enter all recognized directives in the hash table.  */
@@ -2292,3 +2623,12 @@ _cpp_init_directives (cpp_reader *pfile)
       node->directive_index = i;
     }
 }
+
+/* Extract header file from a bracket include. Parsing starts after '<'.
+   The string is malloced and must be freed by the caller.  */
+char *
+_cpp_bracket_include(cpp_reader *pfile)
+{
+  return glue_header_name (pfile);
+}
+