OSDN Git Service

gcc:
authorjsm28 <jsm28@138bc75d-0d04-0410-961f-82ee72b054a4>
Thu, 3 Nov 2005 23:08:18 +0000 (23:08 +0000)
committerjsm28 <jsm28@138bc75d-0d04-0410-961f-82ee72b054a4>
Thu, 3 Nov 2005 23:08:18 +0000 (23:08 +0000)
PR c++/17964
* diagnostic.c (diagnostic_set_info_translated): New function.
(diagnostic_set_info): Use it.  Add comment.
* diagnostic.h (diagnostic_set_info_translated): Declare.

gcc/cp:
* error.c (cp_cpp_error): New function.
* cp-tree.h (cp_cpp_error): Declare.
* parser.c (cp_lexer_new_main): Set CPP option client_diagnostic
and error callback after lexing.

gcc/testsuite:
* g++.dg/cpp/string-1.C: New test.

libcpp:
* include/cpplib.h (struct cpp_options): Add client_diagnostic.
(struct cpp_callbacks): Add error.
* errors.c (cpp_error): If client_diagnostic, use error callback.
* charset.c (convert_escape): Don't use %03o in diagnostic.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@106454 138bc75d-0d04-0410-961f-82ee72b054a4

13 files changed:
gcc/ChangeLog
gcc/cp/ChangeLog
gcc/cp/cp-tree.h
gcc/cp/error.c
gcc/cp/parser.c
gcc/diagnostic.c
gcc/diagnostic.h
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/cpp/string-1.C [new file with mode: 0644]
libcpp/ChangeLog
libcpp/charset.c
libcpp/errors.c
libcpp/include/cpplib.h

index 2935b32..d6e62a6 100644 (file)
@@ -1,3 +1,10 @@
+2005-11-03  Joseph S. Myers  <joseph@codesourcery.com>
+
+       PR c++/17964
+       * diagnostic.c (diagnostic_set_info_translated): New function.
+       (diagnostic_set_info): Use it.  Add comment.
+       * diagnostic.h (diagnostic_set_info_translated): Declare.
+
 2005-11-03  Eric Botcazou  <ebotcazou@adacore.com>
 
        * dwarf2asm.c (dw2_force_const_mem): Add new parameter 'public'.
 2005-11-03  Eric Botcazou  <ebotcazou@adacore.com>
 
        * dwarf2asm.c (dw2_force_const_mem): Add new parameter 'public'.
index 625413b..5d281d3 100644 (file)
@@ -1,3 +1,11 @@
+2005-11-03  Joseph S. Myers  <joseph@codesourcery.com>
+
+       PR c++/17964
+       * error.c (cp_cpp_error): New function.
+       * cp-tree.h (cp_cpp_error): Declare.
+       * parser.c (cp_lexer_new_main): Set CPP option client_diagnostic
+       and error callback after lexing.
+
 2005-11-03  Mark Mitchell  <mark@codesourcery.com>
 
        PR c++/21627
 2005-11-03  Mark Mitchell  <mark@codesourcery.com>
 
        PR c++/21627
index 97cc064..e1ca9f3 100644 (file)
@@ -4437,5 +4437,8 @@ extern void cp_genericize                 (tree);
 #else
 #define ATTRIBUTE_GCC_CXXDIAG(m, n) ATTRIBUTE_NONNULL(m)
 #endif
 #else
 #define ATTRIBUTE_GCC_CXXDIAG(m, n) ATTRIBUTE_NONNULL(m)
 #endif
+extern void cp_cpp_error                       (cpp_reader *, int,
+                                                const char *, va_list)
+     ATTRIBUTE_GCC_CXXDIAG(3,0);
 
 #endif /* ! GCC_CP_TREE_H */
 
 #endif /* ! GCC_CP_TREE_H */
index 8e39cca..d5144b4 100644 (file)
@@ -2327,3 +2327,36 @@ cp_printer (pretty_printer *pp, text_info *text, const char *spec,
 #undef next_lang
 #undef next_int
 }
 #undef next_lang
 #undef next_int
 }
+\f
+/* Callback from cpp_error for PFILE to print diagnostics arising from
+   interpreting strings.  The diagnostic is of type LEVEL; MSG is the
+   translated message and AP the arguments.  */
+
+void
+cp_cpp_error (cpp_reader *pfile ATTRIBUTE_UNUSED, int level,
+             const char *msg, va_list ap)
+{
+  diagnostic_info diagnostic;
+  diagnostic_t dlevel;
+  switch (level)
+    {
+    case CPP_DL_WARNING:
+    case CPP_DL_WARNING_SYSHDR:
+      dlevel = DK_WARNING;
+      break;
+    case CPP_DL_PEDWARN:
+      dlevel = pedantic_error_kind ();
+      break;
+    case CPP_DL_ERROR:
+      dlevel = DK_ERROR;
+      break;
+    case CPP_DL_ICE:
+      dlevel = DK_ICE;
+      break;
+    default:
+      gcc_unreachable ();
+    }
+  diagnostic_set_info_translated (&diagnostic, msg, &ap,
+                                 input_location, dlevel);
+  report_diagnostic (&diagnostic);
+}
index 9821981..bbc5c11 100644 (file)
@@ -297,6 +297,11 @@ cp_lexer_new_main (void)
      string constant concatenation.  */
   c_lex_return_raw_strings = false;
 
      string constant concatenation.  */
   c_lex_return_raw_strings = false;
 
+  /* Subsequent preprocessor diagnostics should use compiler
+     diagnostic functions to get the compiler source location.  */
+  cpp_get_options (parse_in)->client_diagnostic = true;
+  cpp_get_callbacks (parse_in)->error = cp_cpp_error;
+
   gcc_assert (lexer->next_token->type != CPP_PURGED);
   return lexer;
 }
   gcc_assert (lexer->next_token->type != CPP_PURGED);
   return lexer;
 }
index c416010..7f4d814 100644 (file)
@@ -112,19 +112,31 @@ diagnostic_initialize (diagnostic_context *context)
   context->lock = 0;
 }
 
   context->lock = 0;
 }
 
+/* Initialize DIAGNOSTIC, where the message MSG has already been
+   translated.  */
 void
 void
-diagnostic_set_info (diagnostic_info *diagnostic, const char *gmsgid,
-                    va_list *args, location_t location,
-                    diagnostic_t kind)
+diagnostic_set_info_translated (diagnostic_info *diagnostic, const char *msg,
+                               va_list *args, location_t location,
+                               diagnostic_t kind)
 {
   diagnostic->message.err_no = errno;
   diagnostic->message.args_ptr = args;
 {
   diagnostic->message.err_no = errno;
   diagnostic->message.args_ptr = args;
-  diagnostic->message.format_spec = _(gmsgid);
+  diagnostic->message.format_spec = msg;
   diagnostic->location = location;
   diagnostic->kind = kind;
   diagnostic->option_index = 0;
 }
 
   diagnostic->location = location;
   diagnostic->kind = kind;
   diagnostic->option_index = 0;
 }
 
+/* Initialize DIAGNOSTIC, where the message GMSGID has not yet been
+   translated.  */
+void
+diagnostic_set_info (diagnostic_info *diagnostic, const char *gmsgid,
+                    va_list *args, location_t location,
+                    diagnostic_t kind)
+{
+  diagnostic_set_info_translated (diagnostic, _(gmsgid), args, location, kind);
+}
+
 /* Return a malloc'd string describing a location.  The caller is
    responsible for freeing the memory.  */
 char *
 /* Return a malloc'd string describing a location.  The caller is
    responsible for freeing the memory.  */
 char *
index e44d680..3a3204b 100644 (file)
@@ -184,6 +184,10 @@ extern void diagnostic_report_diagnostic (diagnostic_context *,
 #ifdef ATTRIBUTE_GCC_DIAG
 extern void diagnostic_set_info (diagnostic_info *, const char *, va_list *,
                                 location_t, diagnostic_t) ATTRIBUTE_GCC_DIAG(2,0);
 #ifdef ATTRIBUTE_GCC_DIAG
 extern void diagnostic_set_info (diagnostic_info *, const char *, va_list *,
                                 location_t, diagnostic_t) ATTRIBUTE_GCC_DIAG(2,0);
+extern void diagnostic_set_info_translated (diagnostic_info *, const char *,
+                                           va_list *, location_t,
+                                           diagnostic_t)
+     ATTRIBUTE_GCC_DIAG(2,0);
 #endif
 extern char *diagnostic_build_prefix (diagnostic_info *);
 
 #endif
 extern char *diagnostic_build_prefix (diagnostic_info *);
 
index ac49bbc..49d41e1 100644 (file)
@@ -1,5 +1,10 @@
 2005-11-03  Joseph S. Myers  <joseph@codesourcery.com>
 
 2005-11-03  Joseph S. Myers  <joseph@codesourcery.com>
 
+       PR c++/17964
+       * g++.dg/cpp/string-1.C: New test.
+
+2005-11-03  Joseph S. Myers  <joseph@codesourcery.com>
+
        * gcc.target/powerpc: New directory.
        * gcc.target/powerpc/powerpc.exp: New file.
        * gcc.dg/20020118-1.c, gcc.dg/20030218-1.c, gcc.dg/20030505.c,
        * gcc.target/powerpc: New directory.
        * gcc.target/powerpc/powerpc.exp: New file.
        * gcc.dg/20020118-1.c, gcc.dg/20030218-1.c, gcc.dg/20030505.c,
diff --git a/gcc/testsuite/g++.dg/cpp/string-1.C b/gcc/testsuite/g++.dg/cpp/string-1.C
new file mode 100644 (file)
index 0000000..da31330
--- /dev/null
@@ -0,0 +1,9 @@
+// Test location of diagnostics for interpreting strings.  Bug 17964.
+// Origin: Joseph Myers <joseph@codesourcery.com>
+// { dg-do compile }
+
+const char *s = "\q"; // { dg-error "unknown escape sequence" }
+
+const char *t = "\     "; // { dg-error "unknown escape sequence" }
+
+const char *u = "";
index 884002b..c036480 100644 (file)
@@ -1,3 +1,11 @@
+2005-11-03  Joseph S. Myers  <joseph@codesourcery.com>
+
+       PR c++/17964
+       * include/cpplib.h (struct cpp_options): Add client_diagnostic.
+       (struct cpp_callbacks): Add error.
+       * errors.c (cpp_error): If client_diagnostic, use error callback.
+       * charset.c (convert_escape): Don't use %03o in diagnostic.
+
 2005-10-21  James E Wilson  <wilson@specifix.com>
 
        PR preprocessor/15220
 2005-10-21  James E Wilson  <wilson@specifix.com>
 
        PR preprocessor/15220
index 2c87fb6..78c8981 100644 (file)
@@ -1277,8 +1277,14 @@ convert_escape (cpp_reader *pfile, const uchar *from, const uchar *limit,
        cpp_error (pfile, CPP_DL_PEDWARN,
                   "unknown escape sequence '\\%c'", (int) c);
       else
        cpp_error (pfile, CPP_DL_PEDWARN,
                   "unknown escape sequence '\\%c'", (int) c);
       else
-       cpp_error (pfile, CPP_DL_PEDWARN,
-                  "unknown escape sequence: '\\%03o'", (int) c);
+       {
+         /* diagnostic.c does not support "%03o".  When it does, this
+            code can use %03o directly in the diagnostic again.  */
+         char buf[32];
+         sprintf(buf, "%03o", (int) c);
+         cpp_error (pfile, CPP_DL_PEDWARN,
+                    "unknown escape sequence: '\\%s'", buf);
+       }
     }
 
   /* Now convert what we have to the execution character set.  */
     }
 
   /* Now convert what we have to the execution character set.  */
index 477101e..554d9e3 100644 (file)
@@ -140,20 +140,25 @@ cpp_error (cpp_reader * pfile, int level, const char *msgid, ...)
   
   va_start (ap, msgid);
 
   
   va_start (ap, msgid);
 
-  if (CPP_OPTION (pfile, traditional))
-    {
-      if (pfile->state.in_directive)
-       src_loc = pfile->directive_line;
-      else
-       src_loc = pfile->line_table->highest_line;
-    }
+  if (CPP_OPTION (pfile, client_diagnostic))
+    pfile->cb.error (pfile, level, _(msgid), ap);
   else
     {
   else
     {
-      src_loc = pfile->cur_token[-1].src_loc;
-    }
+      if (CPP_OPTION (pfile, traditional))
+       {
+         if (pfile->state.in_directive)
+           src_loc = pfile->directive_line;
+         else
+           src_loc = pfile->line_table->highest_line;
+       }
+      else
+       {
+         src_loc = pfile->cur_token[-1].src_loc;
+       }
 
 
-  if (_cpp_begin_message (pfile, level, src_loc, 0))
-    v_message (msgid, ap);
+      if (_cpp_begin_message (pfile, level, src_loc, 0))
+       v_message (msgid, ap);
+    }
 
   va_end (ap);
 }
 
   va_end (ap);
 }
index 3c4d0d6..c5d8e85 100644 (file)
@@ -435,6 +435,9 @@ struct cpp_options
   /* True means return pragmas as tokens rather than processing
      them directly. */
   bool defer_pragmas;
   /* True means return pragmas as tokens rather than processing
      them directly. */
   bool defer_pragmas;
+
+  /* True means error callback should be used for diagnostics.  */
+  bool client_diagnostic;
 };
 
 /* Callback for header lookup for HEADER, which is the name of a
 };
 
 /* Callback for header lookup for HEADER, which is the name of a
@@ -467,6 +470,11 @@ struct cpp_callbacks
   int (*valid_pch) (cpp_reader *, const char *, int);
   void (*read_pch) (cpp_reader *, const char *, int, const char *);
   missing_header_cb missing_header;
   int (*valid_pch) (cpp_reader *, const char *, int);
   void (*read_pch) (cpp_reader *, const char *, int, const char *);
   missing_header_cb missing_header;
+
+  /* Called to emit a diagnostic if client_diagnostic option is true.
+     This callback receives the translated message.  */
+  void (*error) (cpp_reader *, int, const char *, va_list)
+       ATTRIBUTE_PRINTF(3,0);
 };
 
 /* Chain of directories to look for include files in.  */
 };
 
 /* Chain of directories to look for include files in.  */