re PR preprocessor/61817 (Inconsistent location of tokens in the expansion list of...
authorRichard Henderson <rth@redhat.com>
Wed, 6 Apr 2016 18:35:16 +0000 (11:35 -0700)
committerRichard Henderson <rth@gcc.gnu.org>
Wed, 6 Apr 2016 18:35:16 +0000 (11:35 -0700)
PR preprocessor/61817
PR preprocessor/69391

  * internal.h (_cpp_builtin_macro_text): Update decl.
  * macro.c (_cpp_builtin_macro_text): Accept location for __LINE__.
  (builtin_macro): Accept a second location for __LINE__.
  (enter_macro_context): Compute both virtual and real expansion
  locations for the macro.

  * gcc.dg/pr61817-1.c: New test.
  * gcc.dg/pr61817-2.c: New test.
  * gcc.dg/pr69391-1.c: New test.
  * gcc.dg/pr69391-2.c: New test.

From-SVN: r234794

gcc/testsuite/ChangeLog
gcc/testsuite/gcc.dg/pr61817-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/pr61817-2.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/pr69391-1.c [new file with mode: 0644]
gcc/testsuite/gcc.dg/pr69391-2.c [new file with mode: 0644]
libcpp/ChangeLog
libcpp/internal.h
libcpp/macro.c

index bc9eed1d2901353d4c826e3a5969d2f2aad268cf..0ecced8244895fa12eca79764aba0f65933d8dc9 100644 (file)
@@ -1,3 +1,10 @@
+2016-04-06  Richard Henderson  <rth@redhat.com>
+
+       * gcc.dg/pr61817-1.c: New test.
+       * gcc.dg/pr61817-2.c: New test.
+       * gcc.dg/pr69391-1.c: New test.
+       * gcc.dg/pr69391-2.c: New test.
+
 2016-04-06  Vladimir Makarov  <vmakarov@redhat.com>
 
        PR rtl-optimization/70398
diff --git a/gcc/testsuite/gcc.dg/pr61817-1.c b/gcc/testsuite/gcc.dg/pr61817-1.c
new file mode 100644 (file)
index 0000000..4230485
--- /dev/null
@@ -0,0 +1,19 @@
+/* { dg-do compile } */
+/* { dg-options "-std=c11 -ftrack-macro-expansion=0" } */
+
+#define A(x) _Static_assert(x, #x)
+#define F(x, y, z) a = __LINE__, b = x ## y, c = z
+
+enum {
+#line 10
+    F
+     (
+      __LI,
+      NE__,
+      __LINE__
+      )
+};
+
+A(a == 15);
+A(b == 15);
+A(c == 15);
diff --git a/gcc/testsuite/gcc.dg/pr61817-2.c b/gcc/testsuite/gcc.dg/pr61817-2.c
new file mode 100644 (file)
index 0000000..e4326b8
--- /dev/null
@@ -0,0 +1,19 @@
+/* { dg-do compile } */
+/* { dg-options "-std=c11 -ftrack-macro-expansion=1" } */
+
+#define A(x) _Static_assert(x, #x)
+#define F(x, y, z) a = __LINE__, b = x ## y, c = z
+
+enum {
+#line 10
+    F
+     (
+      __LI,
+      NE__,
+      __LINE__
+      )
+};
+
+A(a == 15);
+A(b == 15);
+A(c == 15);
diff --git a/gcc/testsuite/gcc.dg/pr69391-1.c b/gcc/testsuite/gcc.dg/pr69391-1.c
new file mode 100644 (file)
index 0000000..15e49dc
--- /dev/null
@@ -0,0 +1,12 @@
+/* { dg-do run } */
+/* { dg-additional-options "-ftrack-macro-expansion=0" } */
+#define STR_I(X) #X
+#define STR(X) STR_I(X)
+#define LINE STR(__LINE__) STR(__LINE__)
+int main()
+{
+  const char *s = LINE;
+  if (s[0] != '8' || s[1] != '8')
+    __builtin_abort ();
+  return 0;
+}
diff --git a/gcc/testsuite/gcc.dg/pr69391-2.c b/gcc/testsuite/gcc.dg/pr69391-2.c
new file mode 100644 (file)
index 0000000..7d2faae
--- /dev/null
@@ -0,0 +1,12 @@
+/* { dg-do run } */
+/* { dg-additional-options "-ftrack-macro-expansion=1" } */
+#define STR_I(X) #X
+#define STR(X) STR_I(X)
+#define LINE STR(__LINE__) STR(__LINE__)
+int main()
+{
+  const char *s = LINE;
+  if (s[0] != '8' || s[1] != '8')
+    __builtin_abort ();
+  return 0;
+}
index 49b6e71abbb74e051dd5630c6b20037dca346e22..583f9542eabd6916463ae1a6c2c488bf59a7c721 100644 (file)
@@ -1,3 +1,13 @@
+2016-04-06  Richard Henderson  <rth@redhat.com>
+
+       PR preprocessor/61817
+       PR preprocessor/69391
+       * internal.h (_cpp_builtin_macro_text): Update decl.
+       * macro.c (_cpp_builtin_macro_text): Accept location for __LINE__.
+       (builtin_macro): Accept a second location for __LINE__.
+       (enter_macro_context): Compute both virtual and real expansion
+       locations for the macro.
+
 2016-03-25  Bernd Schmidt  <bschmidt@redhat.com>
 
        PR lto/69650
index bafd48038651e61c82116cf88d576fe71fd4bfa9..9ce870738cc6322362dee020f0e07e03b69991b0 100644 (file)
@@ -626,7 +626,8 @@ extern bool _cpp_save_parameter (cpp_reader *, cpp_macro *, cpp_hashnode *,
 extern bool _cpp_arguments_ok (cpp_reader *, cpp_macro *, const cpp_hashnode *,
                               unsigned int);
 extern const unsigned char *_cpp_builtin_macro_text (cpp_reader *,
-                                                    cpp_hashnode *);
+                                                    cpp_hashnode *,
+                                                    source_location = 0);
 extern int _cpp_warn_if_unused_macro (cpp_reader *, cpp_hashnode *, void *);
 extern void _cpp_push_token_context (cpp_reader *, cpp_hashnode *,
                                     const cpp_token *, unsigned int);
index 759fbe7f028c4299a2270d579d8d6da2b3200cd5..c251553450421fab1983474ddd77b068570de74e 100644 (file)
@@ -93,7 +93,8 @@ struct macro_arg_saved_data {
 
 static int enter_macro_context (cpp_reader *, cpp_hashnode *,
                                const cpp_token *, source_location);
-static int builtin_macro (cpp_reader *, cpp_hashnode *, source_location);
+static int builtin_macro (cpp_reader *, cpp_hashnode *,
+                         source_location, source_location);
 static void push_ptoken_context (cpp_reader *, cpp_hashnode *, _cpp_buff *,
                                 const cpp_token **, unsigned int);
 static void push_extended_tokens_context (cpp_reader *, cpp_hashnode *,
@@ -229,7 +230,8 @@ static const char * const monthnames[] =
 /* Helper function for builtin_macro.  Returns the text generated by
    a builtin macro. */
 const uchar *
-_cpp_builtin_macro_text (cpp_reader *pfile, cpp_hashnode *node)
+_cpp_builtin_macro_text (cpp_reader *pfile, cpp_hashnode *node,
+                        source_location loc)
 {
   const uchar *result = NULL;
   linenum_type number = 1;
@@ -319,11 +321,14 @@ _cpp_builtin_macro_text (cpp_reader *pfile, cpp_hashnode *node)
     case BT_SPECLINE:
       /* If __LINE__ is embedded in a macro, it must expand to the
         line of the macro's invocation, not its definition.
-        Otherwise things like assert() will not work properly.  */
-      number = linemap_get_expansion_line (pfile->line_table,
-                                          CPP_OPTION (pfile, traditional)
-                                          ? pfile->line_table->highest_line
-                                          : pfile->cur_token[-1].src_loc);
+        Otherwise things like assert() will not work properly.
+        See WG14 N1911, WG21 N4220 sec 6.5, and PR 61861.  */
+      if (CPP_OPTION (pfile, traditional))
+       loc = pfile->line_table->highest_line;
+      else
+       loc = linemap_resolve_location (pfile->line_table, loc,
+                                       LRK_MACRO_EXPANSION_POINT, NULL);
+      number = linemap_get_expansion_line (pfile->line_table, loc);
       break;
 
       /* __STDC__ has the value 1 under normal circumstances.
@@ -417,7 +422,8 @@ _cpp_builtin_macro_text (cpp_reader *pfile, cpp_hashnode *node)
    return the token to the caller.  LOC is the location of the expansion
    point of the macro.  */
 static int
-builtin_macro (cpp_reader *pfile, cpp_hashnode *node, source_location loc)
+builtin_macro (cpp_reader *pfile, cpp_hashnode *node,
+              source_location loc, source_location expand_loc)
 {
   const uchar *buf;
   size_t len;
@@ -433,7 +439,7 @@ builtin_macro (cpp_reader *pfile, cpp_hashnode *node, source_location loc)
       return _cpp_do__Pragma (pfile, loc);
     }
 
-  buf = _cpp_builtin_macro_text (pfile, node);
+  buf = _cpp_builtin_macro_text (pfile, node, expand_loc);
   len = ustrlen (buf);
   nbuf = (char *) alloca (len + 1);
   memcpy (nbuf, buf, len);
@@ -456,8 +462,7 @@ builtin_macro (cpp_reader *pfile, cpp_hashnode *node, source_location loc)
       source_location *virt_locs = NULL;
       _cpp_buff *token_buf = tokens_buff_new (pfile, 1, &virt_locs);
       const line_map_macro * map =
-       linemap_enter_macro (pfile->line_table, node,
-                                           token->src_loc, 1);
+       linemap_enter_macro (pfile->line_table, node, loc, 1);
       tokens_buff_add_token (token_buf, virt_locs, token,
                             pfile->line_table->builtin_location,
                             pfile->line_table->builtin_location,
@@ -1231,22 +1236,29 @@ enter_macro_context (cpp_reader *pfile, cpp_hashnode *node,
   pfile->about_to_expand_macro_p = false;
   /* Handle built-in macros and the _Pragma operator.  */
   {
-    source_location loc;
+    source_location loc, expand_loc;
+
     if (/* The top-level macro invocation that triggered the expansion
           we are looking at is with a standard macro ...*/
        !(pfile->top_most_macro_node->flags & NODE_BUILTIN)
        /* ... and it's a function-like macro invocation.  */
        && pfile->top_most_macro_node->value.macro->fun_like)
-      /* Then the location of the end of the macro invocation is the
-        location of the closing parenthesis.  */
-      loc = pfile->cur_token[-1].src_loc;
+      {
+       /* Then the location of the end of the macro invocation is the
+          location of the closing parenthesis.  */
+       loc = pfile->cur_token[-1].src_loc;
+       expand_loc = loc;
+      }
     else
-      /* Otherwise, the location of the end of the macro invocation is
-        the location of the expansion point of that top-level macro
-        invocation.  */
-      loc = location;
+      {
+       /* Otherwise, the location of the end of the macro invocation is
+          the location of the expansion point of that top-level macro
+          invocation.  */
+       loc = location;
+       expand_loc = pfile->invocation_location;
+      }
 
-    return builtin_macro (pfile, node, loc);
+    return builtin_macro (pfile, node, loc, expand_loc);
   }
 }