summaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorjakub <jakub@138bc75d-0d04-0410-961f-82ee72b054a4>2007-09-27 07:24:58 +0000
committerjakub <jakub@138bc75d-0d04-0410-961f-82ee72b054a4>2007-09-27 07:24:58 +0000
commitb8c23db329da6afaebde201237f25c583ba61885 (patch)
treeda9ad83a363c4d770588541c6c1fc6b8fc3e0b7a /gcc
parent8fdca00ada80224bbb584a12e7c5ca8ee333b905 (diff)
downloadgcc-b8c23db329da6afaebde201237f25c583ba61885.tar.gz
* builtins.c (expand_builtin, expand_builtin_object_size,
expand_builtin_memory_chk, maybe_emit_chk_warning, maybe_emit_sprintf_chk_warning): Use new %K format string specifier for diagnostics. * expr.c (expand_expr_real_1): Likewise. * langhooks-def.h (struct diagnostic_info): Add forward decl. (lhd_print_error_function): Add third argument. * langhooks.h (struct diagnostic_info): Add forward decl. (struct lang_hooks): Add third argument to print_error_function. * diagnostic.h (diagnostic_info): Add abstract_origin field. (diagnostic_last_function_changed, diagnostic_set_last_function): Add second argument. (diagnostic_report_current_function): Likewise. * toplev.c (announce_function): Pass NULL as second argument to diagnostic_set_last_function. * diagnostic.c (diagnostic_report_current_function): Add second argument, pass it as third argument to lang_hooks.print_error_function. (default_diagnostic_starter): Pass DIAGNOSTIC as second argument to diagnostic_report_current_function. (diagnostic_report_diagnostic): Initialize diagnostic->abstract_origin and message.abstract_origin. (verbatim): Initialize abstract_origin. * pretty-print.h (text_info): Add abstract_origin field. * pretty-print.c (pp_base_format): Handle %K. * langhooks.c (lhd_print_error_function): Add third argument. If diagnostic->abstract_origin, print virtual backtrace. * c-format.c (gcc_diag_char_table, gcc_tdiag_char_table, gcc_cdiag_char_table, gcc_cxxdiag_char_table): Support %K. (init_dynamic_diag_info): Likewise. cp/ * error.c (cxx_print_error_function): Add third argument, pass it over to lhd_print_error_function. (cp_print_error_function): If diagnostic->abstract_origin, print virtual backtrace. * cp-tree.h (struct diagnostic_info): New forward decl. (cxx_print_error_function): Add third argument. java/ * lang.c (java_print_error_function): Add third argument. testsuite/ * lib/prune.exp: Prune also "^In function .*$" lines and "^ inlined from .*$" lines. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@128830 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog32
-rw-r--r--gcc/builtins.c34
-rw-r--r--gcc/c-format.c20
-rw-r--r--gcc/cp/ChangeLog9
-rw-r--r--gcc/cp/cp-tree.h4
-rw-r--r--gcc/cp/error.c99
-rw-r--r--gcc/diagnostic.c11
-rw-r--r--gcc/diagnostic.h18
-rw-r--r--gcc/expr.c10
-rw-r--r--gcc/java/ChangeLog4
-rw-r--r--gcc/java/lang.c6
-rw-r--r--gcc/langhooks-def.h3
-rw-r--r--gcc/langhooks.c99
-rw-r--r--gcc/langhooks.h4
-rw-r--r--gcc/pretty-print.c28
-rw-r--r--gcc/pretty-print.h1
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/lib/prune.exp3
-rw-r--r--gcc/toplev.c2
19 files changed, 330 insertions, 62 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 2147dedb02b..f6768d8a794 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,35 @@
+2007-09-27 Jakub Jelinek <jakub@redhat.com>
+
+ * builtins.c (expand_builtin, expand_builtin_object_size,
+ expand_builtin_memory_chk, maybe_emit_chk_warning,
+ maybe_emit_sprintf_chk_warning): Use new %K format string specifier
+ for diagnostics.
+ * expr.c (expand_expr_real_1): Likewise.
+ * langhooks-def.h (struct diagnostic_info): Add forward decl.
+ (lhd_print_error_function): Add third argument.
+ * langhooks.h (struct diagnostic_info): Add forward decl.
+ (struct lang_hooks): Add third argument to print_error_function.
+ * diagnostic.h (diagnostic_info): Add abstract_origin field.
+ (diagnostic_last_function_changed, diagnostic_set_last_function): Add
+ second argument.
+ (diagnostic_report_current_function): Likewise.
+ * toplev.c (announce_function): Pass NULL as second argument to
+ diagnostic_set_last_function.
+ * diagnostic.c (diagnostic_report_current_function): Add second
+ argument, pass it as third argument to lang_hooks.print_error_function.
+ (default_diagnostic_starter): Pass DIAGNOSTIC as second argument
+ to diagnostic_report_current_function.
+ (diagnostic_report_diagnostic): Initialize diagnostic->abstract_origin
+ and message.abstract_origin.
+ (verbatim): Initialize abstract_origin.
+ * pretty-print.h (text_info): Add abstract_origin field.
+ * pretty-print.c (pp_base_format): Handle %K.
+ * langhooks.c (lhd_print_error_function): Add third argument. If
+ diagnostic->abstract_origin, print virtual backtrace.
+ * c-format.c (gcc_diag_char_table, gcc_tdiag_char_table,
+ gcc_cdiag_char_table, gcc_cxxdiag_char_table): Support %K.
+ (init_dynamic_diag_info): Likewise.
+
2007-09-26 David Daney <ddaney@avtrex.com>
PR target/33479
diff --git a/gcc/builtins.c b/gcc/builtins.c
index bb43ab61b3d..bafdce0779f 100644
--- a/gcc/builtins.c
+++ b/gcc/builtins.c
@@ -6273,13 +6273,13 @@ expand_builtin (tree exp, rtx target, rtx subtarget, enum machine_mode mode,
case BUILT_IN_VA_ARG_PACK:
/* All valid uses of __builtin_va_arg_pack () are removed during
inlining. */
- error ("invalid use of %<__builtin_va_arg_pack ()%>");
+ error ("%Kinvalid use of %<__builtin_va_arg_pack ()%>", exp);
return const0_rtx;
case BUILT_IN_VA_ARG_PACK_LEN:
/* All valid uses of __builtin_va_arg_pack_len () are removed during
inlining. */
- error ("invalid use of %<__builtin_va_arg_pack_len ()%>");
+ error ("%Kinvalid use of %<__builtin_va_arg_pack_len ()%>", exp);
return const0_rtx;
/* Return the address of the first anonymous stack arg. */
@@ -11466,12 +11466,11 @@ expand_builtin_object_size (tree exp)
tree ost;
int object_size_type;
tree fndecl = get_callee_fndecl (exp);
- location_t locus = EXPR_LOCATION (exp);
if (!validate_arglist (exp, POINTER_TYPE, INTEGER_TYPE, VOID_TYPE))
{
- error ("%Hfirst argument of %D must be a pointer, second integer constant",
- &locus, fndecl);
+ error ("%Kfirst argument of %D must be a pointer, second integer constant",
+ exp, fndecl);
expand_builtin_trap ();
return const0_rtx;
}
@@ -11483,8 +11482,8 @@ expand_builtin_object_size (tree exp)
|| tree_int_cst_sgn (ost) < 0
|| compare_tree_int (ost, 3) > 0)
{
- error ("%Hlast argument of %D is not integer constant between 0 and 3",
- &locus, fndecl);
+ error ("%Klast argument of %D is not integer constant between 0 and 3",
+ exp, fndecl);
expand_builtin_trap ();
return const0_rtx;
}
@@ -11527,9 +11526,8 @@ expand_builtin_memory_chk (tree exp, rtx target, enum machine_mode mode,
if (! integer_all_onesp (size) && tree_int_cst_lt (size, len))
{
- location_t locus = EXPR_LOCATION (exp);
- warning (0, "%Hcall to %D will always overflow destination buffer",
- &locus, get_callee_fndecl (exp));
+ warning (0, "%Kcall to %D will always overflow destination buffer",
+ exp, get_callee_fndecl (exp));
return NULL_RTX;
}
@@ -11636,7 +11634,6 @@ maybe_emit_chk_warning (tree exp, enum built_in_function fcode)
{
int is_strlen = 0;
tree len, size;
- location_t locus;
switch (fcode)
{
@@ -11683,9 +11680,8 @@ maybe_emit_chk_warning (tree exp, enum built_in_function fcode)
src = c_strlen (src, 1);
if (! src || ! host_integerp (src, 1))
{
- locus = EXPR_LOCATION (exp);
- warning (0, "%Hcall to %D might overflow destination buffer",
- &locus, get_callee_fndecl (exp));
+ warning (0, "%Kcall to %D might overflow destination buffer",
+ exp, get_callee_fndecl (exp));
return;
}
else if (tree_int_cst_lt (src, size))
@@ -11694,9 +11690,8 @@ maybe_emit_chk_warning (tree exp, enum built_in_function fcode)
else if (! host_integerp (len, 1) || ! tree_int_cst_lt (size, len))
return;
- locus = EXPR_LOCATION (exp);
- warning (0, "%Hcall to %D will always overflow destination buffer",
- &locus, get_callee_fndecl (exp));
+ warning (0, "%Kcall to %D will always overflow destination buffer",
+ exp, get_callee_fndecl (exp));
}
/* Emit warning if a buffer overflow is detected at compile time
@@ -11754,9 +11749,8 @@ maybe_emit_sprintf_chk_warning (tree exp, enum built_in_function fcode)
if (! tree_int_cst_lt (len, size))
{
- location_t locus = EXPR_LOCATION (exp);
- warning (0, "%Hcall to %D will always overflow destination buffer",
- &locus, get_callee_fndecl (exp));
+ warning (0, "%Kcall to %D will always overflow destination buffer",
+ exp, get_callee_fndecl (exp));
}
}
diff --git a/gcc/c-format.c b/gcc/c-format.c
index b703e47a008..9eaaefa9d5a 100644
--- a/gcc/c-format.c
+++ b/gcc/c-format.c
@@ -561,7 +561,7 @@ static const format_char_info gcc_diag_char_table[] =
{ "H", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q", "", NULL },
/* These will require a "tree" at runtime. */
- { "J", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q", "", NULL },
+ { "JK", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q", "", NULL },
{ "<>'", 0, STD_C89, NOARGUMENTS, "", "", NULL },
{ "m", 0, STD_C89, NOARGUMENTS, "q", "", NULL },
@@ -584,7 +584,7 @@ static const format_char_info gcc_tdiag_char_table[] =
{ "H", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q", "", NULL },
/* These will require a "tree" at runtime. */
- { "DFJT", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q+", "", NULL },
+ { "DFJKT", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q+", "", NULL },
{ "<>'", 0, STD_C89, NOARGUMENTS, "", "", NULL },
{ "m", 0, STD_C89, NOARGUMENTS, "q", "", NULL },
@@ -607,7 +607,7 @@ static const format_char_info gcc_cdiag_char_table[] =
{ "H", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q", "", NULL },
/* These will require a "tree" at runtime. */
- { "DEFJT", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q+", "", NULL },
+ { "DEFJKT", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q+", "", NULL },
{ "<>'", 0, STD_C89, NOARGUMENTS, "", "", NULL },
{ "m", 0, STD_C89, NOARGUMENTS, "q", "", NULL },
@@ -630,7 +630,7 @@ static const format_char_info gcc_cxxdiag_char_table[] =
{ "H", 0, STD_C89, { T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q", "", NULL },
/* These will require a "tree" at runtime. */
- { "ADEFJTV",0,STD_C89,{ T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q+#", "", NULL },
+ { "ADEFJKTV",0,STD_C89,{ T89_V, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q+#", "", NULL },
/* These accept either an 'int' or an 'enum tree_code' (which is handled as an 'int'.) */
{ "CLOPQ",0,STD_C89, { T89_I, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN, BADLEN }, "q", "", NULL },
@@ -2611,6 +2611,9 @@ init_dynamic_diag_info (void)
i = find_char_info_specifier_index (diag_fci, 'J');
diag_fci[i].types[0].type = &t;
diag_fci[i].pointer_count = 1;
+ i = find_char_info_specifier_index (diag_fci, 'K');
+ diag_fci[i].types[0].type = &t;
+ diag_fci[i].pointer_count = 1;
}
/* Handle the __gcc_tdiag__ format specifics. */
@@ -2635,6 +2638,9 @@ init_dynamic_diag_info (void)
i = find_char_info_specifier_index (tdiag_fci, 'J');
tdiag_fci[i].types[0].type = &t;
tdiag_fci[i].pointer_count = 1;
+ i = find_char_info_specifier_index (tdiag_fci, 'K');
+ tdiag_fci[i].types[0].type = &t;
+ tdiag_fci[i].pointer_count = 1;
}
/* Handle the __gcc_cdiag__ format specifics. */
@@ -2659,6 +2665,9 @@ init_dynamic_diag_info (void)
i = find_char_info_specifier_index (cdiag_fci, 'J');
cdiag_fci[i].types[0].type = &t;
cdiag_fci[i].pointer_count = 1;
+ i = find_char_info_specifier_index (cdiag_fci, 'K');
+ cdiag_fci[i].types[0].type = &t;
+ cdiag_fci[i].pointer_count = 1;
}
/* Handle the __gcc_cxxdiag__ format specifics. */
@@ -2683,6 +2692,9 @@ init_dynamic_diag_info (void)
i = find_char_info_specifier_index (cxxdiag_fci, 'J');
cxxdiag_fci[i].types[0].type = &t;
cxxdiag_fci[i].pointer_count = 1;
+ i = find_char_info_specifier_index (cxxdiag_fci, 'K');
+ cxxdiag_fci[i].types[0].type = &t;
+ cxxdiag_fci[i].pointer_count = 1;
}
}
}
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index b47c802399a..915ac9ed986 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,12 @@
+2007-09-27 Jakub Jelinek <jakub@redhat.com>
+
+ * error.c (cxx_print_error_function): Add third argument, pass
+ it over to lhd_print_error_function.
+ (cp_print_error_function): If diagnostic->abstract_origin, print
+ virtual backtrace.
+ * cp-tree.h (struct diagnostic_info): New forward decl.
+ (cxx_print_error_function): Add third argument.
+
2007-09-25 Simon Martin <simartin@users.sourceforge.net>
PR c++/33207
diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h
index 83f4d423231..f28e965465f 100644
--- a/gcc/cp/cp-tree.h
+++ b/gcc/cp/cp-tree.h
@@ -32,6 +32,7 @@ along with GCC; see the file COPYING3. If not see
#include "c-common.h"
#include "name-lookup.h"
struct diagnostic_context;
+struct diagnostic_info;
/* Usage of TREE_LANG_FLAG_?:
0: IDENTIFIER_MARKED (IDENTIFIER_NODEs)
@@ -4138,7 +4139,8 @@ extern void cxx_print_decl (FILE *, tree, int);
extern void cxx_print_type (FILE *, tree, int);
extern void cxx_print_identifier (FILE *, tree, int);
extern void cxx_print_error_function (struct diagnostic_context *,
- const char *);
+ const char *,
+ struct diagnostic_info *);
extern void build_self_reference (void);
extern int same_signature_p (const_tree, const_tree);
extern void maybe_add_class_template_decl_list (tree, tree, int);
diff --git a/gcc/cp/error.c b/gcc/cp/error.c
index 602426a79a1..24f1d83a0c1 100644
--- a/gcc/cp/error.c
+++ b/gcc/cp/error.c
@@ -2329,9 +2329,10 @@ cv_to_string (tree p, int v)
/* Langhook for print_error_function. */
void
-cxx_print_error_function (diagnostic_context *context, const char *file)
+cxx_print_error_function (diagnostic_context *context, const char *file,
+ diagnostic_info *diagnostic)
{
- lhd_print_error_function (context, file);
+ lhd_print_error_function (context, file, diagnostic);
pp_base_set_prefix (context->printer, file);
maybe_print_instantiation_context (context);
}
@@ -2359,23 +2360,105 @@ static void
cp_print_error_function (diagnostic_context *context,
diagnostic_info *diagnostic)
{
- if (diagnostic_last_function_changed (context))
+ if (diagnostic_last_function_changed (context, diagnostic))
{
const char *old_prefix = context->printer->prefix;
const char *file = LOCATION_FILE (diagnostic->location);
- char *new_prefix = file ? file_name_as_prefix (file) : NULL;
+ tree abstract_origin = diagnostic->abstract_origin;
+ char *new_prefix = (file && abstract_origin == NULL)
+ ? file_name_as_prefix (file) : NULL;
pp_base_set_prefix (context->printer, new_prefix);
if (current_function_decl == NULL)
pp_base_string (context->printer, "At global scope:");
else
- pp_printf (context->printer, "In %s %qs:",
- function_category (current_function_decl),
- cxx_printable_name (current_function_decl, 2));
+ {
+ tree fndecl, ao;
+
+ if (abstract_origin)
+ {
+ ao = BLOCK_ABSTRACT_ORIGIN (abstract_origin);
+ while (TREE_CODE (ao) == BLOCK && BLOCK_ABSTRACT_ORIGIN (ao))
+ ao = BLOCK_ABSTRACT_ORIGIN (ao);
+ gcc_assert (TREE_CODE (ao) == FUNCTION_DECL);
+ fndecl = ao;
+ }
+ else
+ fndecl = current_function_decl;
+
+ pp_printf (context->printer, "In %s %qs",
+ function_category (fndecl),
+ cxx_printable_name (fndecl, 2));
+
+ while (abstract_origin)
+ {
+ location_t *locus;
+ tree block = abstract_origin;
+
+ locus = &BLOCK_SOURCE_LOCATION (block);
+ fndecl = NULL;
+ block = BLOCK_SUPERCONTEXT (block);
+ while (block && TREE_CODE (block) == BLOCK
+ && BLOCK_ABSTRACT_ORIGIN (block))
+ {
+ ao = BLOCK_ABSTRACT_ORIGIN (block);
+
+ while (TREE_CODE (ao) == BLOCK && BLOCK_ABSTRACT_ORIGIN (ao))
+ ao = BLOCK_ABSTRACT_ORIGIN (ao);
+
+ if (TREE_CODE (ao) == FUNCTION_DECL)
+ {
+ fndecl = ao;
+ break;
+ }
+ else if (TREE_CODE (ao) != BLOCK)
+ break;
+
+ block = BLOCK_SUPERCONTEXT (block);
+ }
+ if (fndecl)
+ abstract_origin = block;
+ else
+ {
+ while (block && TREE_CODE (block) == BLOCK)
+ block = BLOCK_SUPERCONTEXT (block);
+
+ if (TREE_CODE (block) == FUNCTION_DECL)
+ fndecl = block;
+ abstract_origin = NULL;
+ }
+ if (fndecl)
+ {
+ expanded_location s = expand_location (*locus);
+ pp_base_character (context->printer, ',');
+ pp_base_newline (context->printer);
+ if (s.file != NULL)
+ {
+#ifdef USE_MAPPED_LOCATION
+ if (flag_show_column && s.column != 0)
+ pp_printf (context->printer,
+ " inlined from %qs at %s:%d:%d",
+ cxx_printable_name (fndecl, 2),
+ s.file, s.line, s.column);
+ else
+#endif
+ pp_printf (context->printer,
+ " inlined from %qs at %s:%d",
+ cxx_printable_name (fndecl, 2),
+ s.file, s.line);
+
+ }
+ else
+ pp_printf (context->printer, " inlined from %qs",
+ cxx_printable_name (fndecl, 2));
+ }
+ }
+ pp_base_character (context->printer, ':');
+ }
pp_base_newline (context->printer);
- diagnostic_set_last_function (context);
+ diagnostic_set_last_function (context, diagnostic);
pp_base_destroy_prefix (context->printer);
context->printer->prefix = old_prefix;
}
diff --git a/gcc/diagnostic.c b/gcc/diagnostic.c
index c712608d73b..6bbfe9a36e7 100644
--- a/gcc/diagnostic.c
+++ b/gcc/diagnostic.c
@@ -261,10 +261,11 @@ diagnostic_action_after_output (diagnostic_context *context,
/* Prints out, if necessary, the name of the current function
that caused an error. Called from all error and warning functions. */
void
-diagnostic_report_current_function (diagnostic_context *context)
+diagnostic_report_current_function (diagnostic_context *context,
+ diagnostic_info *diagnostic)
{
diagnostic_report_current_module (context);
- lang_hooks.print_error_function (context, input_filename);
+ lang_hooks.print_error_function (context, input_filename, diagnostic);
}
void
@@ -302,7 +303,7 @@ static void
default_diagnostic_starter (diagnostic_context *context,
diagnostic_info *diagnostic)
{
- diagnostic_report_current_function (context);
+ diagnostic_report_current_function (context, diagnostic);
pp_set_prefix (context->printer, diagnostic_build_prefix (diagnostic));
}
@@ -414,6 +415,8 @@ diagnostic_report_diagnostic (diagnostic_context *context,
" [", cl_options[diagnostic->option_index].opt_text, "]", NULL));
diagnostic->message.locus = &diagnostic->location;
+ diagnostic->message.abstract_origin = &diagnostic->abstract_origin;
+ diagnostic->abstract_origin = NULL;
pp_format (context->printer, &diagnostic->message);
(*diagnostic_starter (context)) (context, diagnostic);
pp_output_formatted_text (context->printer);
@@ -421,6 +424,7 @@ diagnostic_report_diagnostic (diagnostic_context *context,
pp_flush (context->printer);
diagnostic_action_after_output (context, diagnostic);
diagnostic->message.format_spec = saved_format_spec;
+ diagnostic->abstract_origin = NULL;
}
context->lock--;
@@ -472,6 +476,7 @@ verbatim (const char *gmsgid, ...)
text.args_ptr = &ap;
text.format_spec = _(gmsgid);
text.locus = NULL;
+ text.abstract_origin = NULL;
pp_format_verbatim (global_dc->printer, &text);
pp_flush (global_dc->printer);
va_end (ap);
diff --git a/gcc/diagnostic.h b/gcc/diagnostic.h
index 94e5f32eb26..02e43bd0f8e 100644
--- a/gcc/diagnostic.h
+++ b/gcc/diagnostic.h
@@ -37,10 +37,13 @@ typedef enum
/* A diagnostic is described by the MESSAGE to send, the FILE and LINE of
its context and its KIND (ice, error, warning, note, ...) See complete
list in diagnostic.def. */
-typedef struct
+typedef struct diagnostic_info
{
text_info message;
location_t location;
+ /* TREE_BLOCK if the diagnostic is to be reported in some inline
+ function inlined into other function, otherwise NULL. */
+ tree abstract_origin;
/* The kind of diagnostic it is about. */
diagnostic_t kind;
/* Which OPT_* directly controls this diagnostic. */
@@ -137,13 +140,15 @@ struct diagnostic_context
/* True if the last function in which a diagnostic was reported is
different from the current one. */
-#define diagnostic_last_function_changed(DC) \
- ((DC)->last_function != current_function_decl)
+#define diagnostic_last_function_changed(DC, DI) \
+ ((DC)->last_function != ((DI)->abstract_origin \
+ ? (DI)->abstract_origin : current_function_decl))
/* Remember the current function as being the last one in which we report
a diagnostic. */
-#define diagnostic_set_last_function(DC) \
- (DC)->last_function = current_function_decl
+#define diagnostic_set_last_function(DC, DI) \
+ (DC)->last_function = (((DI) && (DI)->abstract_origin) \
+ ? (DI)->abstract_origin : current_function_decl)
/* True if the last module or file in which a diagnostic was reported is
different from the current one. */
@@ -185,7 +190,8 @@ extern diagnostic_context *global_dc;
/* Diagnostic related functions. */
extern void diagnostic_initialize (diagnostic_context *);
extern void diagnostic_report_current_module (diagnostic_context *);
-extern void diagnostic_report_current_function (diagnostic_context *);
+extern void diagnostic_report_current_function (diagnostic_context *,
+ diagnostic_info *);
/* Force diagnostics controlled by OPTIDX to be kind KIND. */
extern diagnostic_t diagnostic_classify_diagnostic (diagnostic_context *,
diff --git a/gcc/expr.c b/gcc/expr.c
index afd01acb4aa..ff3258d746e 100644
--- a/gcc/expr.c
+++ b/gcc/expr.c
@@ -8001,21 +8001,21 @@ expand_expr_real_1 (tree exp, rtx target, enum machine_mode tmode,
/* All valid uses of __builtin_va_arg_pack () are removed during
inlining. */
if (CALL_EXPR_VA_ARG_PACK (exp))
- error ("invalid use of %<__builtin_va_arg_pack ()%>");
+ error ("%Kinvalid use of %<__builtin_va_arg_pack ()%>", exp);
{
tree fndecl = get_callee_fndecl (exp), attr;
if (fndecl
&& (attr = lookup_attribute ("error",
DECL_ATTRIBUTES (fndecl))) != NULL)
- error ("call to %qs declared with attribute error: %s",
- lang_hooks.decl_printable_name (fndecl, 1),
+ error ("%Kcall to %qs declared with attribute error: %s",
+ exp, lang_hooks.decl_printable_name (fndecl, 1),
TREE_STRING_POINTER (TREE_VALUE (TREE_VALUE (attr))));
if (fndecl
&& (attr = lookup_attribute ("warning",
DECL_ATTRIBUTES (fndecl))) != NULL)
- warning (0, "call to %qs declared with attribute warning: %s",
- lang_hooks.decl_printable_name (fndecl, 1),
+ warning (0, "%Kcall to %qs declared with attribute warning: %s",
+ exp, lang_hooks.decl_printable_name (fndecl, 1),
TREE_STRING_POINTER (TREE_VALUE (TREE_VALUE (attr))));
/* Check for a built-in function. */
diff --git a/gcc/java/ChangeLog b/gcc/java/ChangeLog
index 630e9b828e9..bb22fdc36d0 100644
--- a/gcc/java/ChangeLog
+++ b/gcc/java/ChangeLog
@@ -1,3 +1,7 @@
+2007-09-27 Jakub Jelinek <jakub@redhat.com>
+
+ * lang.c (java_print_error_function): Add third argument.
+
2007-09-15 Tom Tromey <tromey@redhat.com>
* java-tree.h (struct lang_decl_func) <function_decl_body>:
diff --git a/gcc/java/lang.c b/gcc/java/lang.c
index 333eb8c32a1..42589062077 100644
--- a/gcc/java/lang.c
+++ b/gcc/java/lang.c
@@ -54,7 +54,8 @@ static bool java_post_options (const char **);
static int java_handle_option (size_t scode, const char *arg, int value);
static void put_decl_string (const char *, int);
static void put_decl_node (tree);
-static void java_print_error_function (diagnostic_context *, const char *);
+static void java_print_error_function (diagnostic_context *, const char *,
+ diagnostic_info *);
static int merge_init_test_initialization (void * *, void *);
static int inline_init_test_initialization (void * *, void *);
static bool java_dump_tree (void *, tree);
@@ -489,7 +490,8 @@ static GTY(()) tree last_error_function_context;
static GTY(()) tree last_error_function;
static void
java_print_error_function (diagnostic_context *context ATTRIBUTE_UNUSED,
- const char *file)
+ const char *file,
+ diagnostic_info *diagnostic ATTRIBUTE_UNUSED)
{
/* Don't print error messages with bogus function prototypes. */
if (inhibit_error_function_printing)
diff --git a/gcc/langhooks-def.h b/gcc/langhooks-def.h
index 28efd6beb49..6eca2f0497f 100644
--- a/gcc/langhooks-def.h
+++ b/gcc/langhooks-def.h
@@ -24,6 +24,7 @@ along with GCC; see the file COPYING3. If not see
#include "hooks.h"
struct diagnostic_context;
+struct diagnostic_info;
/* Note to creators of new hooks:
@@ -53,7 +54,7 @@ extern int lhd_types_compatible_p (tree, tree);
extern rtx lhd_expand_expr (tree, rtx, enum machine_mode, int, rtx *);
extern int lhd_expand_decl (tree);
extern void lhd_print_error_function (struct diagnostic_context *,
- const char *);
+ const char *, struct diagnostic_info *);
extern void lhd_set_decl_assembler_name (tree);
extern bool lhd_warn_unused_global_decl (const_tree);
extern void lhd_incomplete_type_error (const_tree, const_tree);
diff --git a/gcc/langhooks.c b/gcc/langhooks.c
index b8e7aaacc27..4682514508d 100644
--- a/gcc/langhooks.c
+++ b/gcc/langhooks.c
@@ -381,12 +381,15 @@ lhd_initialize_diagnostics (struct diagnostic_context *ctx ATTRIBUTE_UNUSED)
/* The default function to print out name of current function that caused
an error. */
void
-lhd_print_error_function (diagnostic_context *context, const char *file)
+lhd_print_error_function (diagnostic_context *context, const char *file,
+ diagnostic_info *diagnostic)
{
- if (diagnostic_last_function_changed (context))
+ if (diagnostic_last_function_changed (context, diagnostic))
{
const char *old_prefix = context->printer->prefix;
- char *new_prefix = file ? file_name_as_prefix (file) : NULL;
+ tree abstract_origin = diagnostic->abstract_origin;
+ char *new_prefix = (file && abstract_origin == NULL)
+ ? file_name_as_prefix (file) : NULL;
pp_set_prefix (context->printer, new_prefix);
@@ -394,17 +397,95 @@ lhd_print_error_function (diagnostic_context *context, const char *file)
pp_printf (context->printer, _("At top level:"));
else
{
- if (TREE_CODE (TREE_TYPE (current_function_decl)) == METHOD_TYPE)
+ tree fndecl, ao;
+
+ if (abstract_origin)
+ {
+ ao = BLOCK_ABSTRACT_ORIGIN (abstract_origin);
+ while (TREE_CODE (ao) == BLOCK && BLOCK_ABSTRACT_ORIGIN (ao))
+ ao = BLOCK_ABSTRACT_ORIGIN (ao);
+ gcc_assert (TREE_CODE (ao) == FUNCTION_DECL);
+ fndecl = ao;
+ }
+ else
+ fndecl = current_function_decl;
+
+ if (TREE_CODE (TREE_TYPE (fndecl)) == METHOD_TYPE)
pp_printf
- (context->printer, _("In member function %qs:"),
- lang_hooks.decl_printable_name (current_function_decl, 2));
+ (context->printer, _("In member function %qs"),
+ lang_hooks.decl_printable_name (fndecl, 2));
else
pp_printf
- (context->printer, _("In function %qs:"),
- lang_hooks.decl_printable_name (current_function_decl, 2));
+ (context->printer, _("In function %qs"),
+ lang_hooks.decl_printable_name (fndecl, 2));
+
+ while (abstract_origin)
+ {
+ location_t *locus;
+ tree block = abstract_origin;
+
+ locus = &BLOCK_SOURCE_LOCATION (block);
+ fndecl = NULL;
+ block = BLOCK_SUPERCONTEXT (block);
+ while (block && TREE_CODE (block) == BLOCK
+ && BLOCK_ABSTRACT_ORIGIN (block))
+ {
+ ao = BLOCK_ABSTRACT_ORIGIN (block);
+
+ while (TREE_CODE (ao) == BLOCK && BLOCK_ABSTRACT_ORIGIN (ao))
+ ao = BLOCK_ABSTRACT_ORIGIN (ao);
+
+ if (TREE_CODE (ao) == FUNCTION_DECL)
+ {
+ fndecl = ao;
+ break;
+ }
+ else if (TREE_CODE (ao) != BLOCK)
+ break;
+
+ block = BLOCK_SUPERCONTEXT (block);
+ }
+ if (fndecl)
+ abstract_origin = block;
+ else
+ {
+ while (block && TREE_CODE (block) == BLOCK)
+ block = BLOCK_SUPERCONTEXT (block);
+
+ if (TREE_CODE (block) == FUNCTION_DECL)
+ fndecl = block;
+ abstract_origin = NULL;
+ }
+ if (fndecl)
+ {
+ expanded_location s = expand_location (*locus);
+ pp_character (context->printer, ',');
+ pp_newline (context->printer);
+ if (s.file != NULL)
+ {
+#ifdef USE_MAPPED_LOCATION
+ if (flag_show_column && s.column != 0)
+ pp_printf (context->printer,
+ _(" inlined from %qs at %s:%d:%d"),
+ lang_hooks.decl_printable_name (fndecl, 2),
+ s.file, s.line, s.column);
+ else
+#endif
+ pp_printf (context->printer,
+ _(" inlined from %qs at %s:%d"),
+ lang_hooks.decl_printable_name (fndecl, 2),
+ s.file, s.line);
+
+ }
+ else
+ pp_printf (context->printer, _(" inlined from %qs"),
+ lang_hooks.decl_printable_name (fndecl, 2));
+ }
+ }
+ pp_character (context->printer, ':');
}
- diagnostic_set_last_function (context);
+ diagnostic_set_last_function (context, diagnostic);
pp_flush (context->printer);
context->printer->prefix = old_prefix;
free ((char*) new_prefix);
diff --git a/gcc/langhooks.h b/gcc/langhooks.h
index 7efe7425eb8..8a442753b1f 100644
--- a/gcc/langhooks.h
+++ b/gcc/langhooks.h
@@ -24,6 +24,7 @@ along with GCC; see the file COPYING3. If not see
/* This file should be #include-d after tree.h. */
struct diagnostic_context;
+struct diagnostic_info;
struct gimplify_omp_ctx;
@@ -367,7 +368,8 @@ struct lang_hooks
tree (*lang_get_callee_fndecl) (const_tree);
/* Called by report_error_function to print out function name. */
- void (*print_error_function) (struct diagnostic_context *, const char *);
+ void (*print_error_function) (struct diagnostic_context *, const char *,
+ struct diagnostic_info *);
/* Called from expr_size to calculate the size of the value of an
expression in a language-dependent way. Returns a tree for the size
diff --git a/gcc/pretty-print.c b/gcc/pretty-print.c
index 8f55df29a24..c4de15dc21a 100644
--- a/gcc/pretty-print.c
+++ b/gcc/pretty-print.c
@@ -187,6 +187,7 @@ pp_base_indent (pretty_printer *pp)
%Ns: likewise, but length specified as constant in the format string.
%H: location_t.
%J: a decl tree, from which DECL_SOURCE_LOCATION will be recorded.
+ %K: a statement, from which EXPR_LOCATION and TREE_BLOCK will be recorded.
Flag 'q': quote formatted text (must come immediately after '%').
Arguments can be used sequentially, or through %N$ resp. *N$
@@ -486,6 +487,33 @@ pp_base_format (pretty_printer *pp, text_info *text)
}
break;
+ case 'K':
+ {
+ tree t = va_arg (*text->args_ptr, tree), block;
+ gcc_assert (text->locus != NULL);
+ *text->locus = EXPR_LOCATION (t);
+ gcc_assert (text->abstract_origin != NULL);
+ block = TREE_BLOCK (t);
+ *text->abstract_origin = NULL;
+ while (block
+ && TREE_CODE (block) == BLOCK
+ && BLOCK_ABSTRACT_ORIGIN (block))
+ {
+ tree ao = BLOCK_ABSTRACT_ORIGIN (block);
+
+ while (TREE_CODE (ao) == BLOCK && BLOCK_ABSTRACT_ORIGIN (ao))
+ ao = BLOCK_ABSTRACT_ORIGIN (ao);
+
+ if (TREE_CODE (ao) == FUNCTION_DECL)
+ {
+ *text->abstract_origin = block;
+ break;
+ }
+ block = BLOCK_SUPERCONTEXT (block);
+ }
+ }
+ break;
+
case '.':
{
int n;
diff --git a/gcc/pretty-print.h b/gcc/pretty-print.h
index 585b1d52101..039058ee132 100644
--- a/gcc/pretty-print.h
+++ b/gcc/pretty-print.h
@@ -35,6 +35,7 @@ typedef struct
va_list *args_ptr;
int err_no; /* for %m */
location_t *locus;
+ tree *abstract_origin;
} text_info;
/* How often diagnostics are prefixed by their locations:
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 22bdef285df..ec014ea8cc8 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2007-09-27 Jakub Jelinek <jakub@redhat.com>
+
+ * lib/prune.exp: Prune also "^In function .*$" lines and
+ "^ inlined from .*$" lines.
+
2007-09-26 Richard Guenther <rguenther@suse.de>
PR tree-optimization/33563
diff --git a/gcc/testsuite/lib/prune.exp b/gcc/testsuite/lib/prune.exp
index cfce9c2d55f..2e901a08f4d 100644
--- a/gcc/testsuite/lib/prune.exp
+++ b/gcc/testsuite/lib/prune.exp
@@ -20,9 +20,10 @@
proc prune_gcc_output { text } {
#send_user "Before:$text\n"
- regsub -all "(^|\n)\[^\n\]*: In ((static member )?function|member|method|(copy )?constructor|destructor|instantiation|program|subroutine|block-data) \[^\n\]*" $text "" text
+ regsub -all "(^|\n)(\[^\n\]*: )?In ((static member )?function|member|method|(copy )?constructor|destructor|instantiation|program|subroutine|block-data) \[^\n\]*" $text "" text
regsub -all "(^|\n)\[^\n\]*: At (top level|global scope):\[^\n\]*" $text "" text
regsub -all "(^|\n)\[^\n\]*: instantiated from \[^\n\]*" $text "" text
+ regsub -all "(^|\n) inlined from \[^\n\]*" $text "" text
regsub -all "(^|\n)collect2: ld returned \[^\n\]*" $text "" text
regsub -all "(^|\n)collect: re(compiling|linking)\[^\n\]*" $text "" text
regsub -all "(^|\n)Please submit.*instructions\[^\n\]*" $text "" text
diff --git a/gcc/toplev.c b/gcc/toplev.c
index 8c6a68a6522..0d8c82b7ac6 100644
--- a/gcc/toplev.c
+++ b/gcc/toplev.c
@@ -434,7 +434,7 @@ announce_function (tree decl)
fprintf (stderr, " %s", lang_hooks.decl_printable_name (decl, 2));
fflush (stderr);
pp_needs_newline (global_dc->printer) = true;
- diagnostic_set_last_function (global_dc);
+ diagnostic_set_last_function (global_dc, (diagnostic_info *) NULL);
}
}