This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[diagnostics] enable -fshow-column and fix fall out


I've enabled -fshow-column by default, and have a fixed a bunch of
problems that surfaced.  Sorry for the huge patch.  I keep trying to
contain the changes, but everything is so interdependent...

There is some problem with the dejagnu code that is flagging more errors
than are actually there.  I'll be fixing testsuite/*.exp shortly.

I'll concentrate on fixing regressions now.

Committing to branch.
Aldy

	* common.opt (fshow-column): Enable by default.
	* tree-vrp.c (check_array_ref): Use warning_at.
	(check_array_bounds): Use location from call back if expr has no
	location.
	* tree.h: Add location argument to maybe_fold_*.
	* tree-ssa-ccp.c (ccp_fold): Pass location to maybe_fold_*.
	(maybe_fold_offset_to_array_ref): Add location argument and use it.
	(maybe_fold_offset_to_component_ref): Same.
	(maybe_fold_offset_to_reference): Same.
	(maybe_fold_offset_to_address): Same.
	(maybe_fold_stmt_indirect): Same.
	(maybe_fold_stmt_addition): Same.
	(fold_stmt_r): Pass location to maybe_fold_*.
	(fold_gimple_assign): Same.
	* c-tree.h: Add location argument to finish_decl,
	default_function_array_conversion, store_init_value.
	* c-decl.c (define_label): Use error_at.
	(c_make_fname_decl): Pass location to finish_decl.
	(finish_decl): New location argument.
	(build_compound_literal): Pass location to store_init_value.
	(grokdeclarator): Pass location to finish_decl.
	(grokfield): Same.
	* c-typeck.c (array_to_pointer_conversion): New location argument.
	(function_to_pointer_conversion): Same.
	(default_function_array_conversion): Same.
	(parser_build_unary_op): Pass location to overflow_warning.
	(parser_build_binary_op): Same.  Use warning_at.
	(build_unary_op): Pass location to array_to_pointer_conversion.
	(build_c_cast): Pass location to digest_init.
	(build_modify_expr): New location argument.
	(convert_for_assignment): Same.
	(store_init_value): Same.
	(digest_init): Same.
	(output_init_element): Pass location to digest_init and
	array_to_pointer_conversion.
	(c_finish_return): Pass location to convert_for_assignment.
	* gimplify.c (gimplify_conversion): Pass location to
	maybe_fold_offset_to_address.
	* tree-ssa-forwprop.c (forward_propagate_addr_expr_1): Pass location
	to maybe_fold_stmt_addition.
	* c-omp.c (c_finish_omp_atomic): Pass new location to
	build_modify_expr.
	(c_finish_omp_for): Same.
	* c-common.c (overflow_warning): New argument.
	* c-common.h: New argument to build_modify_expr, overflow_warning.
	* c-parser.c (c_parser_declaration_or_fndef): Pass location to
	finish_decl.
	(c_parser_initializer): Pass location to
	default_function_array_conversion.
	(c_parser_initelt): Same.
	(c_parser_initval): Same.
	(c_parser_asm_operands): Same.
	(c_parser_expr_no_commas): Same.  Pass location to build_modify_expr.
	(c_parser_conditional_expression): Same.
	(c_parser_binary_expression): Add location info to stack.  Use it.
	(c_parser_unary_expression): Pass location to
	default_function_array_conversion, parser_build_unary_op,
	build_indirect_ref, c_parser_postfix_expression_after_primary.
	(c_parser_postfix_expression_after_primary): New location argument.
	Use it.
	(c_parser_expression_conv): Pass location to
	default_function_array_conversion.
	(c_parser_expr_list): Same.
	(c_parser_omp_atomic): Same.
	(c_parser_omp_for_loop): Same.


Index: testsuite/ChangeLog.diagnostics

	* gcc.dg/overflow-warn-1.c: Add column info.
	* gcc.dg/c99-tag-3.c: Same.
	* gcc.dg/Wredundant-decls-2.c: Same.
	* gcc.dg/Warray-bounds.c: Same.
	* gcc.dg/func-ptr-conv-1.c: Same.
	* gcc.dg/Wcxx-compat-2.c: Same.
	* gcc.dg/asm-wide-1.c: Same.
	* gcc.dg/cast-function-1.c: Same.
	* gcc.dg/array-10.c: Same.
	* gcc.dg/c99-vla-jump-1.c: Same.
	* gcc.dg/Wshadow-3.c: Same.


Index: objc/ChangeLog.diagnostics

	* objc-act.c (finish_var_decl): Pass location to finish_decl.
	(objc_get_parm_info): Same.
	(get_super_receiver): Same.

Index: cp/ChangeLog.diagnostics

	* typeck.c (cp_build_binary_op): Pass location to overflow_warning.
	(build_modify_expr): New arg.
	* semantics.c (finish_unary_op_expr): Pass location to
	overflow_warning.
	(handle_omp_for_class_iterator): Pass location to build_modify_expr.

Index: tree-vrp.c
===================================================================
--- tree-vrp.c	(revision 144319)
+++ tree-vrp.c	(working copy)
@@ -5035,8 +5035,8 @@ check_array_ref (tree ref, const locatio
           && TREE_CODE (low_sub) == INTEGER_CST
           && tree_int_cst_lt (low_sub, low_bound))
         {
-          warning (OPT_Warray_bounds,
-                   "%Harray subscript is outside array bounds", location);
+          warning_at (*location, OPT_Warray_bounds,
+		      "array subscript is outside array bounds");
           TREE_NO_WARNING (ref) = 1;
         }
     }
@@ -5050,15 +5050,15 @@ check_array_ref (tree ref, const locatio
                                                         0),
                                        up_sub)))
     {
-      warning (OPT_Warray_bounds, "%Harray subscript is above array bounds",
-               location);
+      warning_at (*location, OPT_Warray_bounds,
+		  "array subscript is above array bounds");
       TREE_NO_WARNING (ref) = 1;
     }
   else if (TREE_CODE (low_sub) == INTEGER_CST
            && tree_int_cst_lt (low_sub, low_bound))
     {
-      warning (OPT_Warray_bounds, "%Harray subscript is below array bounds",
-               location);
+      warning_at (*location, OPT_Warray_bounds,
+		  "array subscript is below array bounds");
       TREE_NO_WARNING (ref) = 1;
     }
 }
@@ -5110,16 +5110,24 @@ check_array_bounds (tree *tp, int *walk_
 {
   tree t = *tp;
   struct walk_stmt_info *wi = (struct walk_stmt_info *) data;
-  const location_t *location = (const location_t *) wi->info;
+  location_t location;
+
+  if (EXPR_HAS_LOCATION (t))
+    location = EXPR_LOCATION (t);
+  else
+    {
+      location_t *locp = (location_t *) wi->info;
+      location = *locp;
+    }
 
   *walk_subtree = TRUE;
 
   if (TREE_CODE (t) == ARRAY_REF)
-    check_array_ref (t, location, false /*ignore_off_by_one*/);
+    check_array_ref (t, &location, false /*ignore_off_by_one*/);
 
   if (TREE_CODE (t) == INDIRECT_REF
       || (TREE_CODE (t) == RETURN_EXPR && TREE_OPERAND (t, 0)))
-    search_for_addr_array (TREE_OPERAND (t, 0), location);
+    search_for_addr_array (TREE_OPERAND (t, 0), &location);
 
   if (TREE_CODE (t) == ADDR_EXPR)
     *walk_subtree = FALSE;
Index: tree.h
===================================================================
--- tree.h	(revision 144319)
+++ tree.h	(working copy)
@@ -4761,9 +4761,9 @@ extern void fold_defer_overflow_warnings
 extern void fold_undefer_overflow_warnings (bool, const_gimple, int);
 extern void fold_undefer_and_ignore_overflow_warnings (void);
 extern bool fold_deferring_overflow_warnings_p (void);
-extern tree maybe_fold_offset_to_reference (tree, tree, tree);
-extern tree maybe_fold_offset_to_address (tree, tree, tree);
-extern tree maybe_fold_stmt_addition (tree, tree, tree);
+extern tree maybe_fold_offset_to_reference (location_t, tree, tree, tree);
+extern tree maybe_fold_offset_to_address (location_t, tree, tree, tree);
+extern tree maybe_fold_stmt_addition (location_t, tree, tree, tree);
 
 extern tree force_fit_type_double (tree, unsigned HOST_WIDE_INT, HOST_WIDE_INT,
 				   int, bool);
Index: objc/objc-act.c
===================================================================
--- objc/objc-act.c	(revision 144319)
+++ objc/objc-act.c	(working copy)
@@ -1481,7 +1481,7 @@ start_var_decl (tree type, const char *n
 static void
 finish_var_decl (tree var, tree initializer)
 {
-  finish_decl (var, initializer, NULL_TREE);
+  finish_decl (var, input_location, initializer, NULL_TREE);
   /* Ensure that the variable actually gets output.  */
   mark_decl_referenced (var);
   /* Mark the decl to avoid "defined but not used" warning.  */
@@ -8392,7 +8392,7 @@ objc_get_parm_info (int have_ellipsis)
 
       TREE_CHAIN (parm_info) = NULL_TREE;
       parm_info = pushdecl (parm_info);
-      finish_decl (parm_info, NULL_TREE, NULL_TREE);
+      finish_decl (parm_info, input_location, NULL_TREE, NULL_TREE);
       parm_info = next;
     }
   arg_info = get_parm_info (have_ellipsis);
@@ -8793,14 +8793,15 @@ get_super_receiver (void)
 	/* This prevents `unused variable' warnings when compiling with -Wall.  */
 	TREE_USED (UOBJC_SUPER_decl) = 1;
 	lang_hooks.decls.pushdecl (UOBJC_SUPER_decl);
-        finish_decl (UOBJC_SUPER_decl, NULL_TREE, NULL_TREE);
+        finish_decl (UOBJC_SUPER_decl, input_location, NULL_TREE, NULL_TREE);
 	UOBJC_SUPER_scope = objc_get_current_scope ();
       }
 
       /* Set receiver to self.  */
       super_expr = objc_build_component_ref (UOBJC_SUPER_decl, self_id);
       super_expr = build_modify_expr (input_location, 
-				      super_expr, NOP_EXPR, self_decl);
+				      super_expr, 
+				      NOP_EXPR, input_location, self_decl);
       super_expr_list = super_expr;
 
       /* Set class to begin searching.  */
@@ -8813,6 +8814,7 @@ get_super_receiver (void)
 	     synth_forward_declarations.  */
 
 	  super_expr = build_modify_expr (input_location, super_expr, NOP_EXPR,
+					  input_location,
 					  ((TREE_CODE (objc_method_context)
 					    == INSTANCE_METHOD_DECL)
 					   ? ucls_super_ref
@@ -8867,6 +8869,7 @@ get_super_receiver (void)
 
 	  super_expr
 	    = build_modify_expr (input_location, super_expr, NOP_EXPR,
+				 input_location,
 				 build_c_cast (input_location, 
 					       TREE_TYPE (super_expr),
 					       super_class));
Index: objc/ChangeLog.diagnostics
===================================================================
--- objc/ChangeLog.diagnostics	(revision 144319)
+++ objc/ChangeLog.diagnostics	(working copy)
@@ -1,3 +1,9 @@
+2009-03-05  Aldy Hernandez  <aldyh@redhat.com>
+
+	* objc-act.c (finish_var_decl): Pass location to finish_decl.
+	(objc_get_parm_info): Same.
+	(get_super_receiver): Same.
+
 2008-12-12  Aldy Hernandez  <aldyh@redhat.com>
 
 	* objc-act.c (objc_build_component_ref): Pass location to
Index: testsuite/gcc.dg/overflow-warn-1.c
===================================================================
--- testsuite/gcc.dg/overflow-warn-1.c	(revision 144319)
+++ testsuite/gcc.dg/overflow-warn-1.c	(working copy)
@@ -12,23 +12,23 @@ enum e {
   /* Overflow in an unevaluated part of an expression is OK (example
      in the standard).  */
   E2 = 2 || 1 / 0,
-  E3 = 1 / 0, /* { dg-warning "division by zero" } */
-  /* { dg-error "enumerator value for 'E3' is not an integer constant" "enum error" { target *-*-* } 15 } */
+  E3 = 1 / 0, /* { dg-warning "10:division by zero" } */
+  /* { dg-error "8:enumerator value for 'E3' is not an integer constant" "enum error" { target *-*-* } 15 } */
   /* But as in DR#031, the 1/0 in an evaluated subexpression means the
      whole expression violates the constraints.  */
-  E4 = 0 * (1 / 0), /* { dg-warning "division by zero" } */
+  E4 = 0 * (1 / 0), /* { dg-warning "15:division by zero" } */
   /* { dg-error "enumerator value for 'E4' is not an integer constant" "enum error" { xfail *-*-* } 19 } */
-  E5 = INT_MAX + 1, /* { dg-warning "integer overflow in expression" } */
+  E5 = INT_MAX + 1, /* { dg-warning "16:integer overflow in expression" } */
   /* Again, overflow in evaluated subexpression.  */
-  E6 = 0 * (INT_MAX + 1), /* { dg-warning "integer overflow in expression" } */
+  E6 = 0 * (INT_MAX + 1), /* { dg-warning "21:integer overflow in expression" } */
   /* A cast does not constitute overflow in conversion.  */
   E7 = (char) INT_MAX
 };
 
 struct s {
   int a;
-  int : 0 * (1 / 0); /* { dg-warning "division by zero" } */
-  int : 0 * (INT_MAX + 1); /* { dg-warning "integer overflow in expression" } */
+  int : 0 * (1 / 0); /* { dg-warning "16:division by zero" } */
+  int : 0 * (INT_MAX + 1); /* { dg-warning "22:integer overflow in expression" } */
 };
 
 void
@@ -36,11 +36,11 @@ f (void)
 {
   /* This expression is not required to be a constant expression, so
      it should just involve undefined behavior at runtime.  */
-  int c = INT_MAX + 1; /* { dg-warning "integer overflow in expression" } */
+  int c = INT_MAX + 1; /* { dg-warning "19:integer overflow in expression" } */
 }
 
 /* But this expression does need to be constant.  */
-static int sc = INT_MAX + 1; /* { dg-warning "integer overflow in expression" } */
+static int sc = INT_MAX + 1; /* { dg-warning "25:integer overflow in expression" } */
 
 /* The first two of these involve overflow, so are not null pointer
    constants.  The third has the overflow in an unevaluated
Index: testsuite/gcc.dg/c99-tag-3.c
===================================================================
--- testsuite/gcc.dg/c99-tag-3.c	(revision 144319)
+++ testsuite/gcc.dg/c99-tag-3.c	(working copy)
@@ -13,10 +13,10 @@ void f (void) { struct s0; }
 
 /* A declaration with a qualifier or storage class specifier declares
    the tag if no other declaration of it is visible.  */
-const union u0; /* { dg-warning "useless type qualifier in empty declaration" } */
+const union u0; /* { dg-warning "13:useless type qualifier in empty declaration" } */
 union u0 { long b; };
 
-extern struct s1; /* { dg-warning "useless storage class specifier in empty declaration" } */
+extern struct s1; /* { dg-warning "15:useless storage class specifier in empty declaration" } */
 
 /* But if a declaration of the tag is visible, whether at the same
    scope or an outer scope, the declaration specifies the same type as
@@ -25,13 +25,13 @@ extern struct s1; /* { dg-warning "usele
    the members of an enumeration, it is a constraint violation.  */
 
 struct s2 { char x; };
-const struct s2; /* { dg-error "empty declaration with type qualifier does not redeclare tag" } */
+const struct s2; /* { dg-error "14:empty declaration with type qualifier does not redeclare tag" } */
 
 union u1;
-extern union u1; /* { dg-error "empty declaration with storage class specifier does not redeclare tag" } */
+extern union u1; /* { dg-error "14:empty declaration with storage class specifier does not redeclare tag" } */
 
 union u2 { long b; };
-void g(void) { const union u2; } /* { dg-error "empty declaration with type qualifier does not redeclare tag" } */
+void g(void) { const union u2; } /* { dg-error "28:empty declaration with type qualifier does not redeclare tag" } */
 
 /* And it does not redeclare the tag either if the outer tag is the
    wrong kind of tag.  This also yields an error for the reference to
@@ -39,21 +39,21 @@ void g(void) { const union u2; } /* { dg
    declaration.  */
 
 union u3 { float v; };
-void h(void) { const struct u3; } /* { dg-error "'u3' defined as wrong kind of tag" } */
-/* { dg-error "empty declaration with type qualifier does not redeclare tag" "wrong tag empty" { target *-*-* } 42 } */
+void h(void) { const struct u3; } /* { dg-error "29:'u3' defined as wrong kind of tag" } */
+/* { dg-error "29:empty declaration with type qualifier does not redeclare tag" "wrong tag empty" { target *-*-* } 42 } */
 
 /* However, such useless specifiers are OK if the contents of the tag
    are being defined, or shadowed in an inner scope with the contents
    included in the shadowing.  */
 
 struct s3;
-const struct s3 { int a; }; /* { dg-warning "useless type qualifier in empty declaration" } */
+const struct s3 { int a; }; /* { dg-warning "14:useless type qualifier in empty declaration" } */
 
 union u4;
-extern union u4 { int z; }; /* { dg-warning "useless storage class specifier in empty declaration" } */
+extern union u4 { int z; }; /* { dg-warning "14:useless storage class specifier in empty declaration" } */
 
 enum e0 { E0 };
-void i(void) { const enum e0 { E1 }; } /* { dg-warning "useless type qualifier in empty declaration" } */
+void i(void) { const enum e0 { E1 }; } /* { dg-warning "32:useless type qualifier in empty declaration" } */
 
 union u5 { int p; };
-void j(void) { extern struct u5 { int q; }; } /* { dg-warning "useless storage class specifier in empty declaration" } */
+void j(void) { extern struct u5 { int q; }; } /* { dg-warning "30:useless storage class specifier in empty declaration" } */
Index: testsuite/gcc.dg/Wredundant-decls-2.c
===================================================================
--- testsuite/gcc.dg/Wredundant-decls-2.c	(revision 144319)
+++ testsuite/gcc.dg/Wredundant-decls-2.c	(working copy)
@@ -2,22 +2,22 @@
 /* { dg-do compile } */
 /* { dg-options "-Wredundant-decls" } */
 
-int j = 5; /* { dg-message "note: previous" } */
-int j;     /* { dg-warning "redundant" } */
+int j = 5; /* { dg-message "5:note: previous" } */
+int j;     /* { dg-warning "5:redundant" } */
 
 static int k;
-static int k = 5; /* { dg-message "note: previous" } */
-static int k;     /* { dg-warning "redundant" } */
+static int k = 5; /* { dg-message "12:note: previous" } */
+static int k;     /* { dg-warning "12:redundant" } */
 
-static int l = 5; /* { dg-message "note: previous" } */
-static int l;     /* { dg-warning "redundant" } */
+static int l = 5; /* { dg-message "12:note: previous" } */
+static int l;     /* { dg-warning "12:redundant" } */
 
-static int m;     /* { dg-message "note: previous" } */
-static int m;     /* { dg-warning "redundant" } */
+static int m;     /* { dg-message "12:note: previous" } */
+static int m;     /* { dg-warning "12:redundant" } */
 static int m = 5;
 
-int n;           /* { dg-message "note: previous" } */
-int n;           /* { dg-warning "redundant" } */
+int n;           /* { dg-message "5:note: previous" } */
+int n;           /* { dg-warning "5:redundant" } */
 int n = 5; 
 
 static int o;
Index: testsuite/gcc.dg/Warray-bounds.c
===================================================================
--- testsuite/gcc.dg/Warray-bounds.c	(revision 144319)
+++ testsuite/gcc.dg/Warray-bounds.c	(working copy)
@@ -18,59 +18,59 @@ int* f(void) {
        int c[10];
     } c;
 
-    a[-1] = 0;             /* { dg-warning "array subscript" } */
+    a[-1] = 0;             /* { dg-warning "6:array subscript" } */
     a[ 0] = 0;
     a[ 1] = 0;
 
 
     a[ 9] = 0;
-    a[10] = 0;             /* { dg-warning "array subscript" } */
-    a[11] = 0;             /* { dg-warning "array subscript" } */
-    a[2 * n() - 11] = 0;    /* { dg-warning "array subscript" } */
+    a[10] = 0;             /* { dg-warning "6:array subscript" } */
+    a[11] = 0;             /* { dg-warning "6:array subscript" } */
+    a[2 * n() - 11] = 0;    /* { dg-warning "6:array subscript" } */
     a[2 * n() - 10] = 0;
     a[2 * n() -  1] = 0;
-    a[2 * n() -  0] = 0;    /* { dg-warning "array subscript" } */
+    a[2 * n() -  0] = 0;    /* { dg-warning "6:array subscript" } */
 
-    b[-1] = 0;             /* { dg-warning "array subscript" } */
+    b[-1] = 0;             /* { dg-warning "6:array subscript" } */
     b[ 0] = 0;
     b[ 1] = 0;
     b[ 9] = 0;
-    b[10] = 0;             /* { dg-warning "array subscript" } */
-    b[11] = 0;             /* { dg-warning "array subscript" } */
-    b[2 * n() - 11] = 0;    /* { dg-warning "array subscript" } */
+    b[10] = 0;             /* { dg-warning "6:array subscript" } */
+    b[11] = 0;             /* { dg-warning "6:array subscript" } */
+    b[2 * n() - 11] = 0;    /* { dg-warning "6:array subscript" } */
     b[2 * n() - 10] = 0;
     b[2 * n() -  1] = 0;
-    b[2 * n() -  0] = 0;    /* { dg-warning "array subscript" } */
+    b[2 * n() -  0] = 0;    /* { dg-warning "6:array subscript" } */
 
-    c.c[-1] = 0;           /* { dg-warning "array subscript" } */
+    c.c[-1] = 0;           /* { dg-warning "8:array subscript" } */
     c.c[ 0] = 0;
     c.c[ 1] = 0;
     c.c[ 9] = 0;
-    c.c[10] = 0;           /* { dg-warning "array subscript" } */
-    c.c[11] = 0;           /* { dg-warning "array subscript" } */
-    c.c[2 * n() - 11] = 0;  /* { dg-warning "array subscript" } */
+    c.c[10] = 0;           /* { dg-warning "8:array subscript" } */
+    c.c[11] = 0;           /* { dg-warning "8:array subscript" } */
+    c.c[2 * n() - 11] = 0;  /* { dg-warning "8:array subscript" } */
     c.c[2 * n() - 10] = 0;
     c.c[2 * n() -  1] = 0;
-    c.c[2 * n() -  0] = 0;  /* { dg-warning "array subscript" } */
+    c.c[2 * n() -  0] = 0;  /* { dg-warning "8:array subscript" } */
 
     g(&a[8]);
     g(&a[9]);
     g(&a[10]);
     g(&a[11]);             /* { dg-warning "array subscript" "" { xfail *-*-* } } */
-    g(&a[-30]+10);             /* { dg-warning "array subscript" } */
+    g(&a[-30]+10);             /* { dg-warning "9:array subscript" } */
     g(&a[-30]+30);
 
     g(&b[10]);
     g(&c.c[10]);
     g(&b[11]);             /* { dg-warning "array subscript" "" { xfail *-*-* } } */
-    g(&c.c[11]);           /* { dg-warning "array subscript" } */
+    g(&c.c[11]);           /* { dg-warning "11:array subscript" } */
 
     g(&a[0]);
     g(&b[0]);
     g(&c.c[0]);
 
-    g(&a[-1]);             /* { dg-warning "array subscript" } */
-    g(&b[-1]);             /* { dg-warning "array subscript" } */ 
+    g(&a[-1]);             /* { dg-warning "9:array subscript" } */
+    g(&b[-1]);             /* { dg-warning "9:array subscript" } */ 
     h(sizeof a[-1]);
     h(sizeof a[10]);
     h(sizeof b[-1]);
@@ -86,7 +86,7 @@ int* f(void) {
        c.c[-1] = 0;
 
     for (i = 20; i < 30; ++i)
-             a[i] = 1;       /* { dg-warning "array subscript" } */
+             a[i] = 1;       /* { dg-warning "15:array subscript" } */
 
     return a;
 }
Index: testsuite/gcc.dg/func-ptr-conv-1.c
===================================================================
--- testsuite/gcc.dg/func-ptr-conv-1.c	(revision 144319)
+++ testsuite/gcc.dg/func-ptr-conv-1.c	(working copy)
@@ -9,15 +9,15 @@
 
 void f(void);
 
-void *v1 = f; /* { dg-warning "pointer" "bad conversion" } */
-void *v2 = &f; /* { dg-warning "pointer" "bad conversion" } */
-void *v3 = (void *)f; /* { dg-warning "pointer" "bad conversion" } */
-void *v4 = (void *)&f; /* { dg-warning "pointer" "bad conversion" } */
+void *v1 = f; /* { dg-warning "12:pointer" "bad conversion" } */
+void *v2 = &f; /* { dg-warning "12:pointer" "bad conversion" } */
+void *v3 = (void *)f; /* { dg-warning "12:pointer" "bad conversion" } */
+void *v4 = (void *)&f; /* { dg-warning "12:pointer" "bad conversion" } */
 void *v5;
-char *c1 = f; /* { dg-warning "pointer" "bad conversion" } */
-char *c2 = &f; /* { dg-warning "pointer" "bad conversion" } */
-char *c3 = (char *)f; /* { dg-warning "pointer" "bad conversion" } */
-char *c4 = (char *)&f; /* { dg-warning "pointer" "bad conversion" } */
+char *c1 = f; /* { dg-warning "12:pointer" "bad conversion" } */
+char *c2 = &f; /* { dg-warning "12:pointer" "bad conversion" } */
+char *c3 = (char *)f; /* { dg-warning "12:pointer" "bad conversion" } */
+char *c4 = (char *)&f; /* { dg-warning "12:pointer" "bad conversion" } */
 char *c5;
 void (*fp)(void);
 int a;
@@ -25,20 +25,20 @@ int a;
 void
 g(void)
 {
-  v5 = f; /* { dg-warning "pointer" "bad conversion" } */
-  v5 = &f; /* { dg-warning "pointer" "bad conversion" } */
-  v5 = (void *)f; /* { dg-warning "pointer" "bad conversion" } */
-  v5 = (void *)&f; /* { dg-warning "pointer" "bad conversion" } */
-  c5 = f; /* { dg-warning "pointer" "bad conversion" } */
-  c5 = &f; /* { dg-warning "pointer" "bad conversion" } */
-  c5 = (char *)f; /* { dg-warning "pointer" "bad conversion" } */
-  c5 = (char *)&f; /* { dg-warning "pointer" "bad conversion" } */
-  fp = v5; /* { dg-warning "pointer" "bad conversion" } */
-  fp = c5; /* { dg-warning "pointer" "bad conversion" } */
-  fp = (void (*)(void))v5; /* { dg-warning "pointer" "bad conversion" } */
-  fp = (void (*)(void))c5; /* { dg-warning "pointer" "bad conversion" } */
-  (a ? f : v3); /* { dg-warning "pointer" "bad conversion" } */
-  (a ? v2 : fp); /* { dg-warning "pointer" "bad conversion" } */
+  v5 = f; /* { dg-warning "8:pointer" "bad conversion" } */
+  v5 = &f; /* { dg-warning "8:pointer" "bad conversion" } */
+  v5 = (void *)f; /* { dg-warning "8:pointer" "bad conversion" } */
+  v5 = (void *)&f; /* { dg-warning "8:pointer" "bad conversion" } */
+  c5 = f; /* { dg-warning "8:pointer" "bad conversion" } */
+  c5 = &f; /* { dg-warning "8:pointer" "bad conversion" } */
+  c5 = (char *)f; /* { dg-warning "8:pointer" "bad conversion" } */
+  c5 = (char *)&f; /* { dg-warning "8:pointer" "bad conversion" } */
+  fp = v5; /* { dg-warning "8:pointer" "bad conversion" } */
+  fp = c5; /* { dg-warning "8:pointer" "bad conversion" } */
+  fp = (void (*)(void))v5; /* { dg-warning "8:pointer" "bad conversion" } */
+  fp = (void (*)(void))c5; /* { dg-warning "8:pointer" "bad conversion" } */
+  (a ? f : v3); /* { dg-warning "6:pointer" "bad conversion" } */
+  (a ? v2 : fp); /* { dg-warning "6:pointer" "bad conversion" } */
   /* The following are OK.  */
   fp = 0;
   fp = (void *)0;
Index: testsuite/gcc.dg/Wcxx-compat-2.c
===================================================================
--- testsuite/gcc.dg/Wcxx-compat-2.c	(revision 144319)
+++ testsuite/gcc.dg/Wcxx-compat-2.c	(working copy)
@@ -1,36 +1,36 @@
 /* { dg-options "-Wc++-compat" } */
 
 _Bool foo;			/* This is okay.  */
-int bool;			/* { dg-warning "keyword" } */
-int catch;			/* { dg-warning "keyword" } */
-int char16_t;			/* { dg-warning "keyword" } */
-int char32_t;			/* { dg-warning "keyword" } */
-int class;			/* { dg-warning "keyword" } */
-int const_cast;			/* { dg-warning "keyword" } */
-int decltype;			/* { dg-warning "keyword" } */
-int delete;			/* { dg-warning "keyword" } */
-int dynamic_cast;		/* { dg-warning "keyword" } */
-int explicit;			/* { dg-warning "keyword" } */
-int export;			/* { dg-warning "keyword" } */
-int false;			/* { dg-warning "keyword" } */
-int friend;			/* { dg-warning "keyword" } */
-int mutable;			/* { dg-warning "keyword" } */
-int namespace;			/* { dg-warning "keyword" } */
-int new;			/* { dg-warning "keyword" } */
-int operator;			/* { dg-warning "keyword" } */
-int private;			/* { dg-warning "keyword" } */
-int protected;			/* { dg-warning "keyword" } */
-int public;			/* { dg-warning "keyword" } */
-int reinterpret_cast;		/* { dg-warning "keyword" } */
-int static_assert;		/* { dg-warning "keyword" } */
-int static_cast;		/* { dg-warning "keyword" } */
-int template;			/* { dg-warning "keyword" } */
-int this;			/* { dg-warning "keyword" } */
-int throw;			/* { dg-warning "keyword" } */
-int true;			/* { dg-warning "keyword" } */
-int try;			/* { dg-warning "keyword" } */
-int typename;			/* { dg-warning "keyword" } */
-int typeid;			/* { dg-warning "keyword" } */
-int using;			/* { dg-warning "keyword" } */
-int virtual;			/* { dg-warning "keyword" } */
+int bool;			/* { dg-warning "5:keyword" } */
+int catch;			/* { dg-warning "5:keyword" } */
+int char16_t;			/* { dg-warning "5:keyword" } */
+int char32_t;			/* { dg-warning "5:keyword" } */
+int class;			/* { dg-warning "5:keyword" } */
+int const_cast;			/* { dg-warning "5:keyword" } */
+int decltype;			/* { dg-warning "5:keyword" } */
+int delete;			/* { dg-warning "5:keyword" } */
+int dynamic_cast;		/* { dg-warning "5:keyword" } */
+int explicit;			/* { dg-warning "5:keyword" } */
+int export;			/* { dg-warning "5:keyword" } */
+int false;			/* { dg-warning "5:keyword" } */
+int friend;			/* { dg-warning "5:keyword" } */
+int mutable;			/* { dg-warning "5:keyword" } */
+int namespace;			/* { dg-warning "5:keyword" } */
+int new;			/* { dg-warning "5:keyword" } */
+int operator;			/* { dg-warning "5:keyword" } */
+int private;			/* { dg-warning "5:keyword" } */
+int protected;			/* { dg-warning "5:keyword" } */
+int public;			/* { dg-warning "5:keyword" } */
+int reinterpret_cast;		/* { dg-warning "5:keyword" } */
+int static_assert;		/* { dg-warning "5:keyword" } */
+int static_cast;		/* { dg-warning "5:keyword" } */
+int template;			/* { dg-warning "5:keyword" } */
+int this;			/* { dg-warning "5:keyword" } */
+int throw;			/* { dg-warning "5:keyword" } */
+int true;			/* { dg-warning "5:keyword" } */
+int try;			/* { dg-warning "5:keyword" } */
+int typename;			/* { dg-warning "5:keyword" } */
+int typeid;			/* { dg-warning "5:keyword" } */
+int using;			/* { dg-warning "5:keyword" } */
+int virtual;			/* { dg-warning "5:keyword" } */
 int wchar_t;
Index: testsuite/gcc.dg/asm-wide-1.c
===================================================================
--- testsuite/gcc.dg/asm-wide-1.c	(revision 144319)
+++ testsuite/gcc.dg/asm-wide-1.c	(working copy)
@@ -3,27 +3,27 @@
 /* { dg-do compile } */
 /* { dg-options "" } */
 
-int foo asm (L"bar"); /* { dg-error "wide string literal in 'asm'" } */
+int foo asm (L"bar"); /* { dg-error "14:wide string literal in 'asm'" } */
 
-asm (L"foo"); /* { dg-error "wide string literal in 'asm'" } */
+asm (L"foo"); /* { dg-error "6:wide string literal in 'asm'" } */
 
 void
 f (void)
 {
   int x = 1;
-  asm (L"foo"); /* { dg-error "wide string literal in 'asm'" } */
+  asm (L"foo"); /* { dg-error "8:wide string literal in 'asm'" } */
   asm ("foo" :
-       L"=g" (x)); /* { dg-error "wide string literal in 'asm'" } */
+       L"=g" (x)); /* { dg-error "8:wide string literal in 'asm'" } */
   asm ("foo" : [x]
-       L"=g" (x)); /* { dg-error "wide string literal in 'asm'" } */
+       L"=g" (x)); /* { dg-error "8:wide string literal in 'asm'" } */
   asm ("foo" : [x] "=g" (x),
-       L"=g" (x)); /* { dg-error "wide string literal in 'asm'" } */
+       L"=g" (x)); /* { dg-error "8:wide string literal in 'asm'" } */
   asm ("foo" : :
-       L"g" (x)); /* { dg-error "wide string literal in 'asm'" } */
+       L"g" (x)); /* { dg-error "8:wide string literal in 'asm'" } */
   asm ("foo" : : :
-       L"memory"); /* { dg-error "wide string literal in 'asm'" } */
+       L"memory"); /* { dg-error "8:wide string literal in 'asm'" } */
   asm ("foo" : : : "memory",
-       L"memory"); /* { dg-error "wide string literal in 'asm'" } */
+       L"memory"); /* { dg-error "8:wide string literal in 'asm'" } */
 }
 
 /* Extra errors from the substitution of "" for wide strings: */
Index: testsuite/gcc.dg/cast-function-1.c
===================================================================
--- testsuite/gcc.dg/cast-function-1.c	(revision 144319)
+++ testsuite/gcc.dg/cast-function-1.c	(working copy)
@@ -22,14 +22,14 @@ void bar(void)
   int i;
   str_t s;
 
-  d = ((double (*) (int)) foo1) (i);  /* { dg-warning "non-compatible|abort" } */
-  i = ((int (*) (double)) foo1) (d);  /* { dg-warning "non-compatible|abort" } */
-  s = ((str_t (*) (int)) foo1) (i);   /* { dg-warning "non-compatible|abort" } */
+  d = ((double (*) (int)) foo1) (i);  /* { dg-warning "33:non-compatible|abort" } */
+  i = ((int (*) (double)) foo1) (d);  /* { dg-warning "33:non-compatible|abort" } */
+  s = ((str_t (*) (int)) foo1) (i);   /* { dg-warning "32:non-compatible|abort" } */
   ((void (*) (int)) foo1) (d);        /* { dg-warning "non-compatible|abort" } */
   i = ((int (*) (int)) foo1) (i);     /* { dg-bogus "non-compatible|abort" } */
   (void) foo1 (i);                    /* { dg-bogus "non-compatible|abort" } */
 
-  d = ((double (*) (int)) foo2) (i);  /* { dg-warning "non-compatible|abort" } */
+  d = ((double (*) (int)) foo2) (i);  /* { dg-warning "33:non-compatible|abort" } */
   i = ((int (*) (double)) foo2) (d);  /* { dg-bogus "non-compatible|abort" } */
   s = ((str_t (*) (int)) foo2) (i);   /* { dg-warning "non-compatible|abort" } */
   ((void (*) (int)) foo2) (d);        /* { dg-warning "non-compatible|abort" } */
Index: testsuite/gcc.dg/array-10.c
===================================================================
--- testsuite/gcc.dg/array-10.c	(revision 144319)
+++ testsuite/gcc.dg/array-10.c	(working copy)
@@ -6,28 +6,23 @@
 
 int a;
 
-int b0[a]; /* { dg-error "at file scope" } */
-int (*b1)[a]; /* { dg-error "at file scope" } */
+int b0[a]; /* { dg-error "5:at file scope" } */
+int (*b1)[a]; /* { dg-error "7:at file scope" } */
 int (*b2())[a]; /* { dg-error "at file scope" } */
-struct b3 { int x[a]; }; /* { dg-error "at file scope" } */
-struct b4 { int (*x)[a]; }; /* { dg-error "at file scope" } */
+struct b3 { int x[a]; }; /* { dg-error "17:at file scope" } */
+struct b4 { int (*x)[a]; }; /* { dg-error "19:at file scope" } */
 typeof (int [a]) b5; /* { dg-error "at file scope|outside of any function" } */
 
-int c0[(__SIZE_TYPE__)&a]; /* { dg-error "at file scope" } */
-int (*c1)[(__SIZE_TYPE__)&a]; /* { dg-error "at file scope" } */
-int (*c2())[(__SIZE_TYPE__)&a]; /* { dg-error "at file scope" } */
-struct c3 { int x[(__SIZE_TYPE__)&a]; }; /* { dg-error "at file scope" } */
-struct c4 { int (*x)[(__SIZE_TYPE__)&a]; }; /* { dg-error "at file scope" } */
-typeof (int [(__SIZE_TYPE__)&a]) c5; /* { dg-error "at file scope" } */
+int c0[(__SIZE_TYPE__)&a]; /* { dg-error "5:at file scope" } */
+int (*c1)[(__SIZE_TYPE__)&a]; /* { dg-error "7:at file scope" } */
+int (*c2())[(__SIZE_TYPE__)&a]; /* { dg-error "7:at file scope" } */
+struct c3 { int x[(__SIZE_TYPE__)&a]; }; /* { dg-error "17:at file scope" } */
+struct c4 { int (*x)[(__SIZE_TYPE__)&a]; }; /* { dg-error "19:at file scope" } */
+typeof (int [(__SIZE_TYPE__)&a]) c5; /* { dg-error "34:at file scope" } */
 
-int d0[1/0]; /* { dg-error "at file scope" } */
-/* { dg-warning "division by zero" "" { target *-*-* } 23 } */
-int (*d1)[1/0]; /* { dg-error "at file scope" } */
-/* { dg-warning "division by zero" "" { target *-*-* } 25 } */
-int (*d2())[1/0]; /* { dg-error "at file scope" } */
-/* { dg-warning "division by zero" "" { target *-*-* } 27 } */
-struct d3 { int x[1/0]; }; /* { dg-error "at file scope" } */
-/* { dg-warning "division by zero" "" { target *-*-* } 29 } */
-struct d4 { int (*x)[1/0]; }; /* { dg-error "at file scope" } */
-/* { dg-warning "division by zero" "" { target *-*-* } 31 } */
-typeof (int [1/0]) d5; /* { dg-error "at file scope" } */
+int d0[1/0]; /* { dg-error "5:at file scope" } */ /* { dg-warning "8:division by zero" "" { target *-*-* } 23 } */
+int (*d1)[1/0]; /* { dg-error "7:at file scope" } */ /* { dg-warning "12:division by zero" "" { target *-*-* } 25 } */
+int (*d2())[1/0]; /* { dg-error "7:at file scope" } */ /* { dg-warning "14:division by zero" "" { target *-*-* } 27 } */
+struct d3 { int x[1/0]; }; /* { dg-error "17:at file scope" } */ /* { dg-warning "20:division by zero" "" { target *-*-* } 29 } */
+struct d4 { int (*x)[1/0]; }; /* { dg-error "19:at file scope" } */ /* { dg-warning "23:division by zero" "" { target *-*-* } 31 } */
+typeof (int [1/0]) d5; /* { dg-error "20:at file scope" } */
Index: testsuite/gcc.dg/c99-vla-jump-1.c
===================================================================
--- testsuite/gcc.dg/c99-vla-jump-1.c	(revision 144319)
+++ testsuite/gcc.dg/c99-vla-jump-1.c	(working copy)
@@ -15,11 +15,11 @@
 /* { dg-options "-std=iso9899:1999 -pedantic-errors" } */
 
 void fa0 (int n) {  goto a; a:{ int b[n]; { int c[n]; 0;} { int d[n]; 0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; }
-void fa1 (int n) {  goto a; { int b[n]; a:{ int c[n]; 0;} { int d[n]; 0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "jump into scope of identifier with variably modified type" } */
-void fa2 (int n) {  goto a; { int b[n]; { int c[n]; a:0;} { int d[n]; 0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "jump into scope of identifier with variably modified type" } */
-void fa3 (int n) {  goto a; { int b[n]; { int c[n]; 0;} a:{ int d[n]; 0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "jump into scope of identifier with variably modified type" } */
-void fa4 (int n) {  goto a; { int b[n]; { int c[n]; 0;} { int d[n]; a:0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "jump into scope of identifier with variably modified type" } */
-void fa5 (int n) {  goto a; { int b[n]; { int c[n]; 0;} { int d[n]; 0;} a:; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "jump into scope of identifier with variably modified type" } */
+void fa1 (int n) {  goto a; { int b[n]; a:{ int c[n]; 0;} { int d[n]; 0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "41:jump into scope of identifier with variably modified type" } */
+void fa2 (int n) {  goto a; { int b[n]; { int c[n]; a:0;} { int d[n]; 0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "52:jump into scope of identifier with variably modified type" } */
+void fa3 (int n) {  goto a; { int b[n]; { int c[n]; 0;} a:{ int d[n]; 0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "57:jump into scope of identifier with variably modified type" } */
+void fa4 (int n) {  goto a; { int b[n]; { int c[n]; 0;} { int d[n]; a:0;} ; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "69:jump into scope of identifier with variably modified type" } */
+void fa5 (int n) {  goto a; { int b[n]; { int c[n]; 0;} { int d[n]; 0;} a:; int e[n]; 0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "73:jump into scope of identifier with variably modified type" } */
 void fa6 (int n) {  goto a; { int b[n]; { int c[n]; 0;} { int d[n]; 0;} ; int e[n]; a:0;}; { int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "jump into scope of identifier with variably modified type" } */
 void fa7 (int n) {  goto a; { int b[n]; { int c[n]; 0;} { int d[n]; 0;} ; int e[n]; 0;}; a:{ int f[n]; { int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; }
 void fa8 (int n) {  goto a; { int b[n]; { int c[n]; 0;} { int d[n]; 0;} ; int e[n]; 0;}; { int f[n]; a:{ int g[n]; 0;}; { int h[n]; 0;}; ; int i[n]; 0;}; ; int j[n]; 0; } /* { dg-error "jump into scope of identifier with variably modified type" } */
Index: testsuite/gcc.dg/Wshadow-3.c
===================================================================
--- testsuite/gcc.dg/Wshadow-3.c	(revision 144319)
+++ testsuite/gcc.dg/Wshadow-3.c	(working copy)
@@ -5,17 +5,17 @@
 /* { dg-do compile } */
 /* { dg-options "-std=gnu89 -Wshadow" } */
 
-int v; /* { dg-warning "shadowed declaration" } */
+int v; /* { dg-warning "5:shadowed declaration" } */
 int f1(int v);
-int f2(int v, int x[v]); /* { dg-warning "declaration of 'v' shadows a global declaration" } */
-int f3(int v, int y[sizeof(v)]); /* { dg-warning "declaration of 'v' shadows a global declaration" } */
-int f4(int v) { return 0; } /* { dg-warning "declaration of 'v' shadows a global declaration" } */
-int f5(int v, int x[v]) { return 0; } /* { dg-warning "declaration of 'v' shadows a global declaration" } */
+int f2(int v, int x[v]); /* { dg-warning "12:declaration of 'v' shadows a global declaration" } */
+int f3(int v, int y[sizeof(v)]); /* { dg-warning "12:declaration of 'v' shadows a global declaration" } */
+int f4(int v) { return 0; } /* { dg-warning "12:declaration of 'v' shadows a global declaration" } */
+int f5(int v, int x[v]) { return 0; } /* { dg-warning "12:declaration of 'v' shadows a global declaration" } */
 int f6(int x) { return 0; }
-int f7(v) int v; { return 0; } /* { dg-warning "declaration of 'v' shadows a global declaration" } */
-int f8(v, w) int v; int w[v]; { return 0; } /* { dg-warning "declaration of 'v' shadows a global declaration" } */
+int f7(v) int v; { return 0; } /* { dg-warning "15:declaration of 'v' shadows a global declaration" } */
+int f8(v, w) int v; int w[v]; { return 0; } /* { dg-warning "18:declaration of 'v' shadows a global declaration" } */
 int f9(x) int x; { return 0; }
-int f10(v) { return 0; } /* { dg-warning "declaration of 'v' shadows a global declaration" } */
+int f10(v) { return 0; } /* { dg-warning "9:declaration of 'v' shadows a global declaration" } */
 int f11(int a, int b(int a));
 int f12(int a, int b(int a, int x[a])); /* { dg-warning "declaration of 'a' shadows a parameter" } */
 /* { dg-warning "shadowed declaration" "outer parm" { target *-*-* } 20 } */
Index: testsuite/ChangeLog.diagnostics
===================================================================
--- testsuite/ChangeLog.diagnostics	(revision 144319)
+++ testsuite/ChangeLog.diagnostics	(working copy)
@@ -1,3 +1,17 @@
+2009-03-05  Aldy Hernandez  <aldyh@redhat.com>
+
+	* gcc.dg/overflow-warn-1.c: Add column info.
+	* gcc.dg/c99-tag-3.c: Same.
+	* gcc.dg/Wredundant-decls-2.c: Same.
+	* gcc.dg/Warray-bounds.c: Same.
+	* gcc.dg/func-ptr-conv-1.c: Same.
+	* gcc.dg/Wcxx-compat-2.c: Same.
+	* gcc.dg/asm-wide-1.c: Same.
+	* gcc.dg/cast-function-1.c: Same.
+	* gcc.dg/array-10.c: Same.
+	* gcc.dg/c99-vla-jump-1.c: Same.
+	* gcc.dg/Wshadow-3.c: Same.
+
 2008-12-12  Aldy Hernandez  <aldyh@redhat.com>
 
 	* gcc.dg/gomp/pr27415.c: Move firstprivate diagnostics to correct
Index: cp/typeck.c
===================================================================
--- cp/typeck.c	(revision 144319)
+++ cp/typeck.c	(working copy)
@@ -3970,7 +3970,7 @@ cp_build_binary_op (location_t location,
   if (TREE_OVERFLOW_P (result) 
       && !TREE_OVERFLOW_P (op0) 
       && !TREE_OVERFLOW_P (op1))
-    overflow_warning (result);
+    overflow_warning (location, result);
 
   return result;
 }
@@ -5796,7 +5796,8 @@ cp_build_c_cast (tree type, tree expr, t
 /* For use from the C common bits.  */
 tree
 build_modify_expr (location_t location ATTRIBUTE_UNUSED,
-		   tree lhs, enum tree_code modifycode, tree rhs)
+		   tree lhs, enum tree_code modifycode,
+		   location_t rhs_location ATTRIBUTE_UNUSED, tree rhs)
 {
   return cp_build_modify_expr (lhs, modifycode, rhs, tf_warning_or_error);
 }
Index: cp/ChangeLog.diagnostics
===================================================================
--- cp/ChangeLog.diagnostics	(revision 144319)
+++ cp/ChangeLog.diagnostics	(working copy)
@@ -1,4 +1,12 @@
-i2008-12-12  Aldy Hernandez  <aldyh@redhat.com>
+2009-03-05  Aldy Hernandez  <aldyh@redhat.com>
+
+	* typeck.c (cp_build_binary_op): Pass location to overflow_warning.
+	(build_modify_expr): New arg.
+	* semantics.c (finish_unary_op_expr): Pass location to
+	overflow_warning.
+	(handle_omp_for_class_iterator): Pass location to build_modify_expr.
+
+2008-12-12  Aldy Hernandez  <aldyh@redhat.com>
 
 	* typeck.c (cxx_sizeof_or_alignof_type): Pass location to
 	c_sizeof_or_alignof_type.
Index: cp/semantics.c
===================================================================
--- cp/semantics.c	(revision 144319)
+++ cp/semantics.c	(working copy)
@@ -2099,7 +2099,7 @@ finish_unary_op_expr (enum tree_code cod
       TREE_NEGATED_INT (result) = 1;
     }
   if (TREE_OVERFLOW_P (result) && !TREE_OVERFLOW_P (expr))
-    overflow_warning (result);
+    overflow_warning (input_location, result);
 
   return result;
 }
@@ -4081,7 +4081,7 @@ handle_omp_for_class_iterator (int i, lo
   cond = cp_build_binary_op (elocus,
 			     TREE_CODE (cond), decl, diff,
 			     tf_warning_or_error);
-  incr = build_modify_expr (elocus, decl, PLUS_EXPR, incr);
+  incr = build_modify_expr (elocus, decl, PLUS_EXPR, elocus, incr);
 
   orig_body = *body;
   *body = push_stmt_list ();
Index: tree-ssa-ccp.c
===================================================================
--- tree-ssa-ccp.c	(revision 144319)
+++ tree-ssa-ccp.c	(working copy)
@@ -995,7 +995,8 @@ ccp_fold (gimple stmt)
 		  if (!useless_type_conversion_p (TREE_TYPE (lhs),
 						  TREE_TYPE (op0))
 		      && ((tem = maybe_fold_offset_to_address
-				   (op0, integer_zero_node, TREE_TYPE (lhs)))
+			   (gimple_location (stmt),
+			    op0, integer_zero_node, TREE_TYPE (lhs)))
 			  != NULL_TREE))
 		    return tem;
 		  return op0;
@@ -1032,8 +1033,8 @@ ccp_fold (gimple stmt)
 		  && TREE_CODE (op1) == INTEGER_CST)
 		{
 		  tree lhs = gimple_assign_lhs (stmt);
-		  tree tem = maybe_fold_offset_to_address (op0, op1,
-							   TREE_TYPE (lhs));
+		  tree tem = maybe_fold_offset_to_address
+		    (gimple_location (stmt), op0, op1, TREE_TYPE (lhs));
 		  if (tem != NULL_TREE)
 		    return tem;
 		}
@@ -1574,10 +1575,13 @@ struct gimple_opt_pass pass_ccp = 
 
 /* A subroutine of fold_stmt_r.  Attempts to fold *(A+O) to A[X].
    BASE is an array type.  OFFSET is a byte displacement.  ORIG_TYPE
-   is the desired result type.  */
+   is the desired result type.
+
+   LOC is the location of the original expression.  */
 
 static tree
-maybe_fold_offset_to_array_ref (tree base, tree offset, tree orig_type,
+maybe_fold_offset_to_array_ref (location_t loc, tree base, tree offset,
+				tree orig_type,
 				bool allow_negative_idx)
 {
   tree min_idx, idx, idx_type, elt_offset = integer_zero_node;
@@ -1710,16 +1714,23 @@ maybe_fold_offset_to_array_ref (tree bas
 	   && compare_tree_int (idx, 0) < 0)
     return NULL_TREE;
 
-  return build4 (ARRAY_REF, elt_type, base, idx, NULL_TREE, NULL_TREE);
+  {
+    tree t = build4 (ARRAY_REF, elt_type, base, idx, NULL_TREE, NULL_TREE);
+    SET_EXPR_LOCATION (t, loc);
+    return t;
+  }
 }
 
 
 /* Attempt to fold *(S+O) to S.X.
    BASE is a record type.  OFFSET is a byte displacement.  ORIG_TYPE
-   is the desired result type.  */
+   is the desired result type.
+
+   LOC is the location of the original expression.  */
 
 static tree
-maybe_fold_offset_to_component_ref (tree record_type, tree base, tree offset,
+maybe_fold_offset_to_component_ref (location_t loc, tree record_type,
+				    tree base, tree offset,
 				    tree orig_type, bool base_is_ptr)
 {
   tree f, t, field_type, tail_array_field, field_offset;
@@ -1802,14 +1813,16 @@ maybe_fold_offset_to_component_ref (tree
 	new_base = build1 (INDIRECT_REF, record_type, base);
       else
 	new_base = base;
+      protected_set_expr_location (new_base, loc);
       new_base = build3 (COMPONENT_REF, field_type, new_base, f, NULL_TREE);
+      protected_set_expr_location (new_base, loc);
 
       /* Recurse to possibly find the match.  */
-      ret = maybe_fold_offset_to_array_ref (new_base, t, orig_type,
+      ret = maybe_fold_offset_to_array_ref (loc, new_base, t, orig_type,
 					    f == TYPE_FIELDS (record_type));
       if (ret)
 	return ret;
-      ret = maybe_fold_offset_to_component_ref (field_type, new_base, t,
+      ret = maybe_fold_offset_to_component_ref (loc, field_type, new_base, t,
 						orig_type, false);
       if (ret)
 	return ret;
@@ -1825,25 +1838,32 @@ maybe_fold_offset_to_component_ref (tree
   /* If we get here, we've got an aggregate field, and a possibly 
      nonzero offset into them.  Recurse and hope for a valid match.  */
   if (base_is_ptr)
-    base = build1 (INDIRECT_REF, record_type, base);
+    {
+      base = build1 (INDIRECT_REF, record_type, base);
+      SET_EXPR_LOCATION (base, loc);
+    }
   base = build3 (COMPONENT_REF, field_type, base, f, NULL_TREE);
+  SET_EXPR_LOCATION (base, loc);
 
-  t = maybe_fold_offset_to_array_ref (base, offset, orig_type,
+  t = maybe_fold_offset_to_array_ref (loc, base, offset, orig_type,
 				      f == TYPE_FIELDS (record_type));
   if (t)
     return t;
-  return maybe_fold_offset_to_component_ref (field_type, base, offset,
+  return maybe_fold_offset_to_component_ref (loc, field_type, base, offset,
 					     orig_type, false);
 }
 
 /* Attempt to express (ORIG_TYPE)BASE+OFFSET as BASE->field_of_orig_type
-   or BASE[index] or by combination of those. 
+   or BASE[index] or by combination of those.
+
+   LOC is the location of original expression.
 
    Before attempting the conversion strip off existing ADDR_EXPRs and
    handled component refs.  */
 
 tree
-maybe_fold_offset_to_reference (tree base, tree offset, tree orig_type)
+maybe_fold_offset_to_reference (location_t loc, tree base, tree offset,
+				tree orig_type)
 {
   tree ret;
   tree type;
@@ -1890,13 +1910,17 @@ maybe_fold_offset_to_reference (tree bas
 	return NULL_TREE;
       type = TREE_TYPE (TREE_TYPE (base));
     }
-  ret = maybe_fold_offset_to_component_ref (type, base, offset,
+  ret = maybe_fold_offset_to_component_ref (loc, type, base, offset,
 					    orig_type, base_is_ptr);
   if (!ret)
     {
       if (base_is_ptr)
-	base = build1 (INDIRECT_REF, type, base);
-      ret = maybe_fold_offset_to_array_ref (base, offset, orig_type, true);
+	{
+	  base = build1 (INDIRECT_REF, type, base);
+	  SET_EXPR_LOCATION (base, loc);
+	}
+      ret = maybe_fold_offset_to_array_ref (loc,
+					    base, offset, orig_type, true);
     }
   return ret;
 }
@@ -1904,17 +1928,21 @@ maybe_fold_offset_to_reference (tree bas
 /* Attempt to express (ORIG_TYPE)&BASE+OFFSET as &BASE->field_of_orig_type
    or &BASE[index] or by combination of those.
 
+   LOC is the location of the original expression.
+
    Before attempting the conversion strip off existing component refs.  */
 
 tree
-maybe_fold_offset_to_address (tree addr, tree offset, tree orig_type)
+maybe_fold_offset_to_address (location_t loc, tree addr, tree offset,
+			      tree orig_type)
 {
   tree t;
 
   gcc_assert (POINTER_TYPE_P (TREE_TYPE (addr))
 	      && POINTER_TYPE_P (orig_type));
 
-  t = maybe_fold_offset_to_reference (addr, offset, TREE_TYPE (orig_type));
+  t = maybe_fold_offset_to_reference (loc, addr, offset,
+				      TREE_TYPE (orig_type));
   if (t != NULL_TREE)
     {
       tree orig = addr;
@@ -1952,7 +1980,9 @@ maybe_fold_offset_to_address (tree addr,
       ptr_type = build_pointer_type (TREE_TYPE (t));
       if (!useless_type_conversion_p (orig_type, ptr_type))
 	return NULL_TREE;
-      return build_fold_addr_expr_with_type (t, ptr_type);
+      t = build_fold_addr_expr_with_type (t, ptr_type);
+      protected_set_expr_location (t, loc);
+      return t;
     }
 
   return NULL_TREE;
@@ -1966,6 +1996,7 @@ maybe_fold_stmt_indirect (tree expr, tre
 {
   tree t;
   bool volatile_p = TREE_THIS_VOLATILE (expr);
+  location_t loc = EXPR_LOCATION (expr);
 
   /* We may well have constructed a double-nested PLUS_EXPR via multiple
      substitutions.  Fold that down to one.  Remove NON_LVALUE_EXPRs that
@@ -2006,7 +2037,7 @@ maybe_fold_stmt_indirect (tree expr, tre
 	return DECL_INITIAL (base);
 
       /* Try folding *(&B+O) to B.X.  */
-      t = maybe_fold_offset_to_reference (base_addr, offset,
+      t = maybe_fold_offset_to_reference (loc, base_addr, offset,
 					  TREE_TYPE (expr));
       if (t)
 	{
@@ -2045,7 +2076,7 @@ maybe_fold_stmt_indirect (tree expr, tre
       /* Try folding *(B+O) to B->X.  Still an improvement.  */
       if (POINTER_TYPE_P (TREE_TYPE (base)))
 	{
-          t = maybe_fold_offset_to_reference (base, offset,
+          t = maybe_fold_offset_to_reference (loc, base, offset,
 				              TREE_TYPE (expr));
 	  if (t)
 	    return t;
@@ -2070,7 +2101,7 @@ maybe_fold_stmt_indirect (tree expr, tre
    which may be able to propagate further.  */
 
 tree
-maybe_fold_stmt_addition (tree res_type, tree op0, tree op1)
+maybe_fold_stmt_addition (location_t loc, tree res_type, tree op0, tree op1)
 {
   tree ptd_type;
   tree t;
@@ -2134,12 +2165,15 @@ maybe_fold_stmt_addition (tree res_type,
     ptd_type = TREE_TYPE (TREE_TYPE (op0));
 
   /* At which point we can try some of the same things as for indirects.  */
-  t = maybe_fold_offset_to_array_ref (op0, op1, ptd_type, true);
+  t = maybe_fold_offset_to_array_ref (loc, op0, op1, ptd_type, true);
   if (!t)
-    t = maybe_fold_offset_to_component_ref (TREE_TYPE (op0), op0, op1,
+    t = maybe_fold_offset_to_component_ref (loc, TREE_TYPE (op0), op0, op1,
 					    ptd_type, false);
   if (t)
-    t = build1 (ADDR_EXPR, res_type, t);
+    {
+      t = build1 (ADDR_EXPR, res_type, t);
+      SET_EXPR_LOCATION (t, loc);
+    }
 
   return t;
 }
@@ -2201,7 +2235,8 @@ fold_stmt_r (tree *expr_p, int *walk_sub
       if (POINTER_TYPE_P (TREE_TYPE (expr))
           && POINTER_TYPE_P (TREE_TYPE (TREE_TYPE (expr)))
 	  && POINTER_TYPE_P (TREE_TYPE (TREE_OPERAND (expr, 0)))
-	  && (t = maybe_fold_offset_to_address (TREE_OPERAND (expr, 0),
+	  && (t = maybe_fold_offset_to_address (EXPR_LOCATION (expr),
+						TREE_OPERAND (expr, 0),
 						integer_zero_node,
 						TREE_TYPE (TREE_TYPE (expr)))))
 	return t;
@@ -2270,7 +2305,8 @@ fold_stmt_r (tree *expr_p, int *walk_sub
         return t;
       *walk_subtrees = 0;
 
-      t = maybe_fold_stmt_addition (TREE_TYPE (expr),
+      t = maybe_fold_stmt_addition (EXPR_LOCATION (expr),
+				    TREE_TYPE (expr),
                                     TREE_OPERAND (expr, 0),
                                     TREE_OPERAND (expr, 1));
       break;
@@ -2700,7 +2736,8 @@ fold_gimple_assign (gimple_stmt_iterator
 		 && POINTER_TYPE_P (TREE_TYPE (gimple_assign_rhs1 (stmt))))
 	  {
 	    tree type = gimple_expr_type (stmt);
-	    tree t = maybe_fold_offset_to_address (gimple_assign_rhs1 (stmt),
+	    tree t = maybe_fold_offset_to_address (gimple_location (stmt),
+						   gimple_assign_rhs1 (stmt),
 						   integer_zero_node, type);
 	    if (t)
 	      return t;
@@ -2720,7 +2757,8 @@ fold_gimple_assign (gimple_stmt_iterator
 		    (TREE_TYPE (gimple_assign_lhs (stmt)), type))
 		type = TREE_TYPE (gimple_assign_rhs1 (stmt));
 	    }
-	  result = maybe_fold_stmt_addition (type,
+	  result = maybe_fold_stmt_addition (gimple_location (stmt),
+					     type,
 					     gimple_assign_rhs1 (stmt),
 					     gimple_assign_rhs2 (stmt));
 	}
Index: c-tree.h
===================================================================
--- c-tree.h	(revision 144319)
+++ c-tree.h	(working copy)
@@ -472,7 +472,7 @@ extern void undeclared_variable (locatio
 extern tree declare_label (tree);
 extern tree define_label (location_t, tree);
 extern void c_maybe_initialize_eh (void);
-extern void finish_decl (tree, tree, tree);
+extern void finish_decl (tree, location_t, tree, tree);
 extern tree finish_enum (tree, tree, tree);
 extern void finish_function (void);
 extern tree finish_struct (location_t, tree, tree, tree);
@@ -549,7 +549,8 @@ extern bool c_vla_type_p (const_tree);
 extern bool c_mark_addressable (tree);
 extern void c_incomplete_type_error (const_tree, const_tree);
 extern tree c_type_promotes_to (tree);
-extern struct c_expr default_function_array_conversion (struct c_expr);
+extern struct c_expr default_function_array_conversion (location_t,
+    							struct c_expr);
 extern tree composite_type (tree, tree);
 extern tree build_component_ref (location_t, tree, tree);
 extern tree build_array_ref (location_t, tree, tree);
@@ -566,7 +567,7 @@ extern tree build_conditional_expr (loca
 extern tree build_compound_expr (location_t, tree, tree);
 extern tree c_cast_expr (location_t, struct c_type_name *, tree);
 extern tree build_c_cast (location_t, tree, tree);
-extern void store_init_value (tree, tree);
+extern void store_init_value (location_t, tree, tree);
 extern void error_init (const char *);
 extern void pedwarn_init (location_t, int opt, const char *);
 extern void maybe_warn_string_init (tree, struct c_expr);
Index: c-decl.c
===================================================================
--- c-decl.c	(revision 144319)
+++ c-decl.c	(working copy)
@@ -2578,7 +2578,7 @@ define_label (location_t location, tree 
 	  || (DECL_CONTEXT (label) != current_function_decl
 	      && C_DECLARED_LABEL_FLAG (label))))
     {
-      error ("%Hduplicate label %qD", &location, label);
+      error_at (location, "duplicate label %qD", label);
       locate_old_decl (label);
       return 0;
     }
@@ -2588,10 +2588,10 @@ define_label (location_t location, tree 
 	 but not defined.  Update its location to point to this
 	 definition.  */
       if (C_DECL_UNDEFINABLE_STMT_EXPR (label))
-	error ("%Jjump into statement expression", label);
+	error_at (location, "jump into statement expression");
       if (C_DECL_UNDEFINABLE_VM (label))
-	error ("%Jjump into scope of identifier with variably modified type",
-	       label);
+	error_at (location,
+		  "jump into scope of identifier with variably modified type");
       DECL_SOURCE_LOCATION (label) = location;
     }
   else
@@ -2605,8 +2605,9 @@ define_label (location_t location, tree 
     }
 
   if (!in_system_header && lookup_name (name))
-    warning (OPT_Wtraditional, "%Htraditional C lacks a separate namespace "
-	     "for labels, identifier %qE conflicts", &location, name);
+    warning_at (location, OPT_Wtraditional,
+		"traditional C lacks a separate namespace "
+		"for labels, identifier %qE conflicts", name);
 
   nlist_se = XOBNEW (&parser_obstack, struct c_label_list);
   nlist_se->next = label_context_stack_se->labels_def;
@@ -2808,7 +2809,7 @@ c_make_fname_decl (location_t loc, tree 
 	    /*invisible=*/false, /*nested=*/false);
     }
 
-  finish_decl (decl, init, NULL_TREE);
+  finish_decl (decl, loc, init, NULL_TREE);
 
   return decl;
 }
@@ -3368,10 +3369,12 @@ c_maybe_initialize_eh (void)
 /* Finish processing of a declaration;
    install its initial value.
    If the length of an array type is not known before,
-   it must be determined now, from the initial value, or it is an error.  */
+   it must be determined now, from the initial value, or it is an error.
+
+   INIT_LOC is the location of the initial value.  */
 
 void
-finish_decl (tree decl, tree init, tree asmspec_tree)
+finish_decl (tree decl, location_t init_loc, tree init, tree asmspec_tree)
 {
   tree type;
   int was_incomplete = (DECL_SIZE (decl) == 0);
@@ -3393,7 +3396,7 @@ finish_decl (tree decl, tree init, tree 
     init = 0;
 
   if (init)
-    store_init_value (decl, init);
+    store_init_value (init_loc, decl, init);
 
   if (c_dialect_objc () && (TREE_CODE (decl) == VAR_DECL
 			    || TREE_CODE (decl) == FUNCTION_DECL
@@ -3695,7 +3698,7 @@ push_parm_decl (const struct c_parm *par
 
   decl = pushdecl (decl);
 
-  finish_decl (decl, NULL_TREE, NULL_TREE);
+  finish_decl (decl, input_location, NULL_TREE, NULL_TREE);
 }
 
 /* Mark all the parameter declarations to date as forward decls.
@@ -3744,7 +3747,7 @@ build_compound_literal (location_t loc, 
   TREE_USED (decl) = 1;
   TREE_TYPE (decl) = type;
   TREE_READONLY (decl) = TYPE_READONLY (type);
-  store_init_value (decl, init);
+  store_init_value (loc, decl, init);
 
   if (TREE_CODE (type) == ARRAY_TYPE && !COMPLETE_TYPE_P (type))
     {
@@ -4623,7 +4626,7 @@ grokdeclarator (const struct c_declarato
 		tree decl = build_decl (loc, TYPE_DECL, NULL_TREE, type);
 		DECL_ARTIFICIAL (decl) = 1;
 		pushdecl (decl);
-		finish_decl (decl, NULL_TREE, NULL_TREE);
+		finish_decl (decl, loc, NULL_TREE, NULL_TREE);
 		TYPE_NAME (type) = decl;
 	      }
 
@@ -5467,7 +5470,7 @@ grokfield (location_t loc,
 			  width ? &width : NULL, decl_attrs,
 			  DEPRECATED_NORMAL);
 
-  finish_decl (value, NULL_TREE, NULL_TREE);
+  finish_decl (value, loc, NULL_TREE, NULL_TREE);
   DECL_INITIAL (value) = width;
 
   return value;
Index: c-typeck.c
===================================================================
--- c-typeck.c	(revision 144319)
+++ c-typeck.c	(working copy)
@@ -83,15 +83,15 @@ static tree decl_constant_value_for_brok
 static tree lookup_field (tree, tree);
 static int convert_arguments (int, tree *, tree, tree, tree, tree);
 static tree pointer_diff (tree, tree);
-static tree convert_for_assignment (tree, tree, enum impl_conv, tree, tree,
-				    int);
+static tree convert_for_assignment (location_t, tree, tree, enum impl_conv,
+				    tree, tree, int);
 static tree valid_compound_expr_initializer (tree, tree);
 static void push_string (const char *);
 static void push_member_name (tree);
 static int spelling_length (void);
 static char *print_spelling (char *);
 static void warning_init (int, const char *);
-static tree digest_init (tree, tree, bool, int);
+static tree digest_init (location_t, tree, tree, bool, int);
 static void output_init_element (tree, bool, tree, tree, int, bool);
 static void output_pending_init_elements (int);
 static int set_designator (int);
@@ -1582,7 +1582,7 @@ decl_constant_value_for_broken_optimizat
 
 /* Convert the array expression EXP to a pointer.  */
 static tree
-array_to_pointer_conversion (tree exp)
+array_to_pointer_conversion (location_t loc, tree exp)
 {
   tree orig_exp = exp;
   tree type = TREE_TYPE (exp);
@@ -1617,13 +1617,13 @@ array_to_pointer_conversion (tree exp)
 
   /* This way is better for a COMPONENT_REF since it can
      simplify the offset for a component.  */
-  adr = build_unary_op (EXPR_LOCATION (exp), ADDR_EXPR, exp, 1);
+  adr = build_unary_op (loc, ADDR_EXPR, exp, 1);
   return convert (ptrtype, adr);
 }
 
 /* Convert the function expression EXP to a pointer.  */
 static tree
-function_to_pointer_conversion (tree exp)
+function_to_pointer_conversion (location_t loc, tree exp)
 {
   tree orig_exp = exp;
 
@@ -1634,15 +1634,17 @@ function_to_pointer_conversion (tree exp
   if (TREE_NO_WARNING (orig_exp))
     TREE_NO_WARNING (exp) = 1;
 
-  return build_unary_op (EXPR_LOCATION (exp), ADDR_EXPR, exp, 0);
+  return build_unary_op (loc, ADDR_EXPR, exp, 0);
 }
 
 /* Perform the default conversion of arrays and functions to pointers.
    Return the result of converting EXP.  For any other expression, just
-   return EXP after removing NOPs.  */
+   return EXP after removing NOPs.
+
+   LOC is the location of the expression.  */
 
 struct c_expr
-default_function_array_conversion (struct c_expr exp)
+default_function_array_conversion (location_t loc, struct c_expr exp)
 {
   tree orig_exp = exp.value;
   tree type = TREE_TYPE (exp.value);
@@ -1677,11 +1679,11 @@ default_function_array_conversion (struc
 	    return exp;
 	  }
 
-	exp.value = array_to_pointer_conversion (exp.value);
+	exp.value = array_to_pointer_conversion (loc, exp.value);
       }
       break;
     case FUNCTION_TYPE:
-      exp.value = function_to_pointer_conversion (exp.value);
+      exp.value = function_to_pointer_conversion (loc, exp.value);
       break;
     default:
       STRIP_TYPE_NOPS (exp.value);
@@ -2386,7 +2388,7 @@ build_function_call (location_t loc, tre
       fundecl = function;
     }
   if (TREE_CODE (TREE_TYPE (function)) == FUNCTION_TYPE)
-    function = function_to_pointer_conversion (function);
+    function = function_to_pointer_conversion (loc, function);
 
   /* For Objective-C, convert any calls via a cast to OBJC_TYPE_REF
      expressions, like those used for ObjC messenger dispatches.  */
@@ -2661,7 +2663,8 @@ convert_arguments (int nargs, tree *arga
 			   and the actual arg is that enum type.  */
 			;
 		      else if (formal_prec != TYPE_PRECISION (type1))
-			warning (OPT_Wtraditional_conversion, "passing argument %d of %qE "
+			warning (OPT_Wtraditional_conversion,
+				 "passing argument %d of %qE "
 				 "with different width due to prototype",
 				 argnum, rname);
 		      else if (TYPE_UNSIGNED (type) == TYPE_UNSIGNED (type1))
@@ -2684,16 +2687,19 @@ convert_arguments (int nargs, tree *arga
 			       && TYPE_UNSIGNED (TREE_TYPE (val)))
 			;
 		      else if (TYPE_UNSIGNED (type))
-			warning (OPT_Wtraditional_conversion, "passing argument %d of %qE "
+			warning (OPT_Wtraditional_conversion,
+				 "passing argument %d of %qE "
 				 "as unsigned due to prototype",
 				 argnum, rname);
 		      else
-			warning (OPT_Wtraditional_conversion, "passing argument %d of %qE "
+			warning (OPT_Wtraditional_conversion,
+				 "passing argument %d of %qE "
 				 "as signed due to prototype", argnum, rname);
 		    }
 		}
 
-	      parmval = convert_for_assignment (type, val, ic_argpass,
+	      parmval = convert_for_assignment (input_location, type, val,
+						ic_argpass,
 						fundecl, function,
 						parmnum + 1);
 
@@ -2757,7 +2763,7 @@ parser_build_unary_op (location_t loc, e
   result.original_code = code;
   
   if (TREE_OVERFLOW_P (result.value) && !TREE_OVERFLOW_P (arg.value))
-    overflow_warning (result.value);
+    overflow_warning (loc, result.value);
 
   return result;
 }
@@ -2803,16 +2809,18 @@ parser_build_binary_op (location_t locat
     {
       if ((code1 == STRING_CST && !integer_zerop (arg2.value))
 	  || (code2 == STRING_CST && !integer_zerop (arg1.value)))
-	warning (OPT_Waddress, "comparison with string literal results in unspecified behavior");
+	warning_at (location, OPT_Waddress,
+		    "comparison with string literal results in unspecified behavior");
     }
   else if (TREE_CODE_CLASS (code) == tcc_comparison
 	   && (code1 == STRING_CST || code2 == STRING_CST))
-    warning (OPT_Waddress, "comparison with string literal results in unspecified behavior");
+    warning_at (location, OPT_Waddress,
+		"comparison with string literal results in unspecified behavior");
 
   if (TREE_OVERFLOW_P (result.value) 
       && !TREE_OVERFLOW_P (arg1.value) 
       && !TREE_OVERFLOW_P (arg2.value))
-    overflow_warning (result.value);
+    overflow_warning (location, result.value);
 
   return result;
 }
@@ -3192,7 +3200,8 @@ build_unary_op (location_t location,
 	    return error_mark_node;
 	  return build_binary_op (location, PLUS_EXPR,
 				  (TREE_CODE (TREE_TYPE (op0)) == ARRAY_TYPE
-				   ? array_to_pointer_conversion (op0)
+				   ? array_to_pointer_conversion (location,
+								  op0)
 				   : op0),
 				  TREE_OPERAND (arg, 1), 1);
 	}
@@ -3694,7 +3703,7 @@ build_c_cast (location_t loc, tree type,
 	  tree t;
 
 	  pedwarn (loc, OPT_pedantic, "ISO C forbids casts to union type");
-	  t = digest_init (type,
+	  t = digest_init (loc, type,
 			   build_constructor_single (type, field, value),
 			   true, 0);
 	  TREE_CONSTANT (t) = TREE_CONSTANT (value);
@@ -3880,11 +3889,13 @@ c_cast_expr (location_t loc, struct c_ty
    to combine the old value of LHS with RHS to get the new value.
    Or else MODIFYCODE is NOP_EXPR meaning do a simple assignment.
 
-   LOCATION is the location of the MODIFYCODE operator.  */
+   LOCATION is the location of the MODIFYCODE operator.
+   RHS_LOC is the location of the RHS.  */
 
 tree
 build_modify_expr (location_t location,
-		   tree lhs, enum tree_code modifycode, tree rhs)
+		   tree lhs, enum tree_code modifycode,
+		   location_t rhs_loc, tree rhs)
 {
   tree result;
   tree newrhs;
@@ -3949,7 +3960,7 @@ build_modify_expr (location_t location,
 
   /* Convert new value to destination type.  */
 
-  newrhs = convert_for_assignment (lhstype, newrhs, ic_assign,
+  newrhs = convert_for_assignment (rhs_loc, lhstype, newrhs, ic_assign,
 				   NULL_TREE, NULL_TREE, 0);
   if (TREE_CODE (newrhs) == ERROR_MARK)
     return error_mark_node;
@@ -3979,7 +3990,7 @@ build_modify_expr (location_t location,
   if (olhstype == TREE_TYPE (result))
     return result;
 
-  result = convert_for_assignment (olhstype, result, ic_assign,
+  result = convert_for_assignment (location, olhstype, result, ic_assign,
 				   NULL_TREE, NULL_TREE, 0);
   protected_set_expr_location (result, location);
   return result;
@@ -3993,11 +4004,13 @@ build_modify_expr (location_t location,
    ERRTYPE says whether it is argument passing, assignment,
    initialization or return.
 
+   LOC is the location of the RHS.
    FUNCTION is a tree for the function being called.
    PARMNUM is the number of the argument, for printing in error messages.  */
 
 static tree
-convert_for_assignment (tree type, tree rhs, enum impl_conv errtype,
+convert_for_assignment (location_t loc, tree type, tree rhs,
+			enum impl_conv errtype,
 			tree fundecl, tree function, int parmnum)
 {
   enum tree_code codel = TREE_CODE (type);
@@ -4028,25 +4041,24 @@ convert_for_assignment (tree type, tree 
   /* This macro is used to emit diagnostics to ensure that all format
      strings are complete sentences, visible to gettext and checked at
      compile time.  */
-#define WARN_FOR_ASSIGNMENT(LOCATION, OPT, AR, AS, IN, RE)               \
+#define WARN_FOR_ASSIGNMENT(OPT, AR, AS, IN, RE)               		 \
   do {                                                                   \
     switch (errtype)                                                     \
       {                                                                  \
       case ic_argpass:                                                   \
-        if (pedwarn (LOCATION, OPT, AR, parmnum, rname))                 \
-          inform ((fundecl && !DECL_IS_BUILTIN (fundecl))                \
-		  ? DECL_SOURCE_LOCATION (fundecl) : LOCATION,           \
+        if (pedwarn (loc, OPT, AR, parmnum, rname))                      \
+          inform (loc,						         \
                   "expected %qT but argument is of type %qT",            \
                   type, rhstype);                                        \
         break;                                                           \
       case ic_assign:                                                    \
-        pedwarn (LOCATION, OPT, AS);                                     \
+        pedwarn (loc, OPT, AS);                                          \
         break;                                                           \
       case ic_init:                                                      \
-        pedwarn (LOCATION, OPT, IN);                                     \
+        pedwarn (loc, OPT, IN);                                          \
         break;                                                           \
       case ic_return:                                                    \
-        pedwarn (LOCATION, OPT, RE);                                     \
+        pedwarn (loc, OPT, RE);                                     	 \
         break;                                                           \
       default:                                                           \
         gcc_unreachable ();                                              \
@@ -4101,7 +4113,7 @@ convert_for_assignment (tree type, tree 
 	 an unprototyped function, it is compile-time undefined;
 	 making it a constraint in that case was rejected in
 	 DR#252.  */
-      error ("void value not ignored as it ought to be");
+      error_at (loc, "void value not ignored as it ought to be");
       return error_mark_node;
     }
   rhs = require_complete_type (rhs);
@@ -4115,12 +4127,13 @@ convert_for_assignment (tree type, tree 
     {
       if (!lvalue_p (rhs))
 	{
-	  error ("cannot pass rvalue to reference parameter");
+	  error_at (loc, "cannot pass rvalue to reference parameter");
 	  return error_mark_node;
 	}
       if (!c_mark_addressable (rhs))
 	return error_mark_node;
       rhs = build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (rhs)), rhs);
+      SET_EXPR_LOCATION (rhs, loc);
 
       /* We already know that these two types are compatible, but they
 	 may not be exactly identical.  In fact, `TREE_TYPE (type)' is
@@ -4128,9 +4141,13 @@ convert_for_assignment (tree type, tree 
 	 likely to be va_list, a typedef to __builtin_va_list, which
 	 is different enough that it will cause problems later.  */
       if (TREE_TYPE (TREE_TYPE (rhs)) != TREE_TYPE (type))
-	rhs = build1 (NOP_EXPR, build_pointer_type (TREE_TYPE (type)), rhs);
+	{
+	  rhs = build1 (NOP_EXPR, build_pointer_type (TREE_TYPE (type)), rhs);
+	  SET_EXPR_LOCATION (rhs, loc);
+	}
 
       rhs = build1 (NOP_EXPR, type, rhs);
+      SET_EXPR_LOCATION (rhs, loc);
       return rhs;
     }
   /* Some types can interconvert without explicit casts.  */
@@ -4228,7 +4245,7 @@ convert_for_assignment (tree type, tree 
 		     function where an ordinary one is wanted, but not
 		     vice-versa.  */
 		  if (TYPE_QUALS (ttl) & ~TYPE_QUALS (ttr))
-		    WARN_FOR_ASSIGNMENT (input_location, 0,
+		    WARN_FOR_ASSIGNMENT (0,
 					 G_("passing argument %d of %qE "
 					    "makes qualified function "
 					    "pointer from unqualified"),
@@ -4242,7 +4259,7 @@ convert_for_assignment (tree type, tree 
 					    "pointer from unqualified"));
 		}
 	      else if (TYPE_QUALS (ttr) & ~TYPE_QUALS (ttl))
-		WARN_FOR_ASSIGNMENT (input_location, 0,
+		WARN_FOR_ASSIGNMENT (0,
 				     G_("passing argument %d of %qE discards "
 					"qualifiers from pointer target type"),
 				     G_("assignment discards qualifiers "
@@ -4256,7 +4273,7 @@ convert_for_assignment (tree type, tree 
 	    }
 
 	  if (!fundecl || !DECL_IN_SYSTEM_HEADER (fundecl))
-	    pedwarn (input_location, OPT_pedantic, 
+	    pedwarn (loc, OPT_pedantic, 
 		     "ISO C prohibits argument conversion to union type");
 
 	  rhs = fold_convert (TREE_TYPE (memb), rhs);
@@ -4290,8 +4307,8 @@ convert_for_assignment (tree type, tree 
 
 	 where NULL is typically defined in C to be '(void *) 0'.  */
       if (VOID_TYPE_P (ttr) && rhs != null_pointer_node && !VOID_TYPE_P (ttl))
-	warning (OPT_Wc___compat, "request for implicit conversion from "
-		 "%qT to %qT not permitted in C++", rhstype, type);
+	warning_at (loc, OPT_Wc___compat, "request for implicit conversion "
+		    "from %qT to %qT not permitted in C++", rhstype, type);
 
       /* Check if the right-hand side has a format attribute but the
 	 left-hand side doesn't.  */
@@ -4301,25 +4318,25 @@ convert_for_assignment (tree type, tree 
 	  switch (errtype)
 	  {
 	  case ic_argpass:
-	    warning (OPT_Wmissing_format_attribute,
-		     "argument %d of %qE might be "
-		     "a candidate for a format attribute",
-		     parmnum, rname);
+	    warning_at (loc, OPT_Wmissing_format_attribute,
+			"argument %d of %qE might be "
+			"a candidate for a format attribute",
+			parmnum, rname);
 	    break;
 	  case ic_assign:
-	    warning (OPT_Wmissing_format_attribute,
-		     "assignment left-hand side might be "
-		     "a candidate for a format attribute");
+	    warning_at (loc, OPT_Wmissing_format_attribute,
+			"assignment left-hand side might be "
+			"a candidate for a format attribute");
 	    break;
 	  case ic_init:
-	    warning (OPT_Wmissing_format_attribute,
-		     "initialization left-hand side might be "
-		     "a candidate for a format attribute");
+	    warning_at (loc, OPT_Wmissing_format_attribute,
+			"initialization left-hand side might be "
+			"a candidate for a format attribute");
 	    break;
 	  case ic_return:
-	    warning (OPT_Wmissing_format_attribute,
-		     "return type might be "
-		     "a candidate for a format attribute");
+	    warning_at (loc, OPT_Wmissing_format_attribute,
+			"return type might be "
+			"a candidate for a format attribute");
 	    break;
 	  default:
 	    gcc_unreachable ();
@@ -4341,7 +4358,7 @@ convert_for_assignment (tree type, tree 
 		  (VOID_TYPE_P (ttr)
 		   && !null_pointer_constant_p (rhs)
 		   && TREE_CODE (ttl) == FUNCTION_TYPE)))
-	    WARN_FOR_ASSIGNMENT (input_location, OPT_pedantic,
+	    WARN_FOR_ASSIGNMENT (OPT_pedantic,
 				 G_("ISO C forbids passing argument %d of "
 				    "%qE between function pointer "
 				    "and %<void *%>"),
@@ -4362,7 +4379,7 @@ convert_for_assignment (tree type, tree 
 		     qualifier are acceptable if the 'volatile' has been added
 		     in by the Objective-C EH machinery.  */
 		  if (!objc_type_quals_match (ttl, ttr))
-		    WARN_FOR_ASSIGNMENT (input_location, 0,
+		    WARN_FOR_ASSIGNMENT (0,
 					 G_("passing argument %d of %qE discards "
 					    "qualifiers from pointer target type"),
 					 G_("assignment discards qualifiers "
@@ -4379,7 +4396,7 @@ convert_for_assignment (tree type, tree 
 		;
 	      /* If there is a mismatch, do warn.  */
 	      else if (warn_pointer_sign)
-		WARN_FOR_ASSIGNMENT (input_location, OPT_Wpointer_sign,
+		WARN_FOR_ASSIGNMENT (OPT_Wpointer_sign,
 				     G_("pointer targets in passing argument "
 					"%d of %qE differ in signedness"),
 				     G_("pointer targets in assignment "
@@ -4397,7 +4414,7 @@ convert_for_assignment (tree type, tree 
 		 it is okay to use a const or volatile function
 		 where an ordinary one is wanted, but not vice-versa.  */
 	      if (TYPE_QUALS (ttl) & ~TYPE_QUALS (ttr))
-		WARN_FOR_ASSIGNMENT (input_location, 0,
+		WARN_FOR_ASSIGNMENT (0,
 				     G_("passing argument %d of %qE makes "
 					"qualified function pointer "
 					"from unqualified"),
@@ -4412,7 +4429,7 @@ convert_for_assignment (tree type, tree 
       else
 	/* Avoid warning about the volatile ObjC EH puts on decls.  */
 	if (!objc_ok)
-	  WARN_FOR_ASSIGNMENT (input_location, 0,
+	  WARN_FOR_ASSIGNMENT (0,
 			       G_("passing argument %d of %qE from "
 				  "incompatible pointer type"),
 			       G_("assignment from incompatible pointer type"),
@@ -4426,7 +4443,7 @@ convert_for_assignment (tree type, tree 
     {
       /* ??? This should not be an error when inlining calls to
 	 unprototyped functions.  */
-      error ("invalid use of non-lvalue array");
+      error_at (loc, "invalid use of non-lvalue array");
       return error_mark_node;
     }
   else if (codel == POINTER_TYPE && coder == INTEGER_TYPE)
@@ -4435,7 +4452,7 @@ convert_for_assignment (tree type, tree 
 	 or one that results from arithmetic, even including
 	 a cast to integer type.  */
       if (!null_pointer_constant_p (rhs))
-	WARN_FOR_ASSIGNMENT (input_location, 0,
+	WARN_FOR_ASSIGNMENT (0,
 			     G_("passing argument %d of %qE makes "
 				"pointer from integer without a cast"),
 			     G_("assignment makes pointer from integer "
@@ -4449,7 +4466,7 @@ convert_for_assignment (tree type, tree 
     }
   else if (codel == INTEGER_TYPE && coder == POINTER_TYPE)
     {
-      WARN_FOR_ASSIGNMENT (input_location, 0,
+      WARN_FOR_ASSIGNMENT (0,
 			   G_("passing argument %d of %qE makes integer "
 			      "from pointer without a cast"),
 			   G_("assignment makes integer from pointer "
@@ -4466,22 +4483,22 @@ convert_for_assignment (tree type, tree 
   switch (errtype)
     {
     case ic_argpass:
-      error ("incompatible type for argument %d of %qE", parmnum, rname);
+      error_at (loc, "incompatible type for argument %d of %qE", parmnum, rname);
       inform ((fundecl && !DECL_IS_BUILTIN (fundecl))
-	      ? DECL_SOURCE_LOCATION (fundecl) : input_location,
+	      ? DECL_SOURCE_LOCATION (fundecl) : loc,
 	      "expected %qT but argument is of type %qT", type, rhstype);
       break;
     case ic_assign:
-      error ("incompatible types when assigning to type %qT from type %qT",
-	     type, rhstype);
+      error_at (loc, "incompatible types when assigning to type %qT from "
+		"type %qT", type, rhstype);
       break;
     case ic_init:
-      error ("incompatible types when initializing type %qT using type %qT",
-	     type, rhstype);
+      error_at (loc, "incompatible types when initializing type %qT using type "
+		"%qT", type, rhstype);
       break;
     case ic_return:
-      error ("incompatible types when returning type %qT but %qT was expected",
-	     rhstype, type);
+      error_at (loc, "incompatible types when returning type %qT but %qT was "
+		"expected", rhstype, type);
       break;
     default:
       gcc_unreachable ();
@@ -4516,10 +4533,12 @@ valid_compound_expr_initializer (tree va
 /* Perform appropriate conversions on the initial value of a variable,
    store it in the declaration DECL,
    and print any error messages that are appropriate.
-   If the init is invalid, store an ERROR_MARK.  */
+   If the init is invalid, store an ERROR_MARK.
+
+   INIT_LOC is the location of the initial value.  */
 
 void
-store_init_value (tree decl, tree init)
+store_init_value (location_t init_loc, tree decl, tree init)
 {
   tree value, type;
 
@@ -4531,7 +4550,7 @@ store_init_value (tree decl, tree init)
 
   /* Digest the specified initializer into an expression.  */
 
-  value = digest_init (type, init, true, TREE_STATIC (decl));
+  value = digest_init (init_loc, type, init, true, TREE_STATIC (decl));
 
   /* Store the expression if valid; else report error.  */
 
@@ -4766,11 +4785,14 @@ maybe_warn_string_init (tree type, struc
    unparenthesized or we should not warn here for it being parenthesized.
    For other types of INIT, STRICT_STRING is not used.
 
+   INIT_LOC is the location of the INIT.
+
    REQUIRE_CONSTANT requests an error if non-constant initializers or
    elements are seen.  */
 
 static tree
-digest_init (tree type, tree init, bool strict_string, int require_constant)
+digest_init (location_t init_loc, tree type, tree init,
+	     bool strict_string, int require_constant)
 {
   enum tree_code code = TREE_CODE (type);
   tree inside_init = init;
@@ -4920,7 +4942,8 @@ digest_init (tree type, tree init, bool 
 	    {
 	      if (TREE_CODE (inside_init) == STRING_CST
 		  || TREE_CODE (inside_init) == COMPOUND_LITERAL_EXPR)
-		inside_init = array_to_pointer_conversion (inside_init);
+		inside_init = array_to_pointer_conversion
+		  (input_location, inside_init);
 	      else
 		{
 		  error_init ("invalid use of non-lvalue array");
@@ -4983,7 +5006,8 @@ digest_init (tree type, tree init, bool 
 
       /* Added to enable additional -Wmissing-format-attribute warnings.  */
       if (TREE_CODE (TREE_TYPE (inside_init)) == POINTER_TYPE)
-	inside_init = convert_for_assignment (type, inside_init, ic_init, NULL_TREE,
+	inside_init = convert_for_assignment (init_loc,
+					      type, inside_init, ic_init, NULL_TREE,
 					      NULL_TREE, 0);
       return inside_init;
     }
@@ -4997,9 +5021,9 @@ digest_init (tree type, tree init, bool 
       if (TREE_CODE (TREE_TYPE (init)) == ARRAY_TYPE
 	  && (TREE_CODE (init) == STRING_CST
 	      || TREE_CODE (init) == COMPOUND_LITERAL_EXPR))
-	init = array_to_pointer_conversion (init);
+	init = array_to_pointer_conversion (input_location, init);
       inside_init
-	= convert_for_assignment (type, init, ic_init,
+	= convert_for_assignment (init_loc, type, init, ic_init,
 				  NULL_TREE, NULL_TREE, 0);
 
       /* Check to see if we have already given an error message.  */
@@ -6366,7 +6390,7 @@ output_init_element (tree value, bool st
 	   && INTEGRAL_TYPE_P (TREE_TYPE (type)))
       && !comptypes (TYPE_MAIN_VARIANT (TREE_TYPE (value)),
 		     TYPE_MAIN_VARIANT (type)))
-    value = array_to_pointer_conversion (value);
+    value = array_to_pointer_conversion (input_location, value);
 
   if (TREE_CODE (value) == COMPOUND_LITERAL_EXPR
       && require_constant_value && !flag_isoc99 && pending)
@@ -6411,7 +6435,8 @@ output_init_element (tree value, bool st
 		  || TREE_CHAIN (field)))))
     return;
 
-  value = digest_init (type, value, strict_string, require_constant_value);
+  value = digest_init (input_location, type, value, strict_string,
+		       require_constant_value);
   if (value == error_mark_node)
     {
       constructor_erroneous = 1;
@@ -7247,7 +7272,8 @@ c_finish_return (location_t loc, tree re
     }
   else
     {
-      tree t = convert_for_assignment (valtype, retval, ic_return,
+      tree t = convert_for_assignment (input_location,
+				       valtype, retval, ic_return,
 				       NULL_TREE, NULL_TREE, 0);
       tree res = DECL_RESULT (current_function_decl);
       tree inner;
Index: gimplify.c
===================================================================
--- gimplify.c	(revision 144319)
+++ gimplify.c	(working copy)
@@ -1833,7 +1833,7 @@ gimplify_conversion (tree *expr_p)
 {
   tree tem;
   gcc_assert (CONVERT_EXPR_P (*expr_p));
-  
+
   /* Then strip away all but the outermost conversion.  */
   STRIP_SIGN_NOPS (TREE_OPERAND (*expr_p, 0));
 
@@ -1848,8 +1848,8 @@ gimplify_conversion (tree *expr_p)
       && POINTER_TYPE_P (TREE_TYPE (*expr_p))
       && POINTER_TYPE_P (TREE_TYPE (TREE_OPERAND (*expr_p, 0)))
       && (tem = maybe_fold_offset_to_address
-		  (TREE_OPERAND (*expr_p, 0),
-		   integer_zero_node, TREE_TYPE (*expr_p))) != NULL_TREE)
+	  (EXPR_LOCATION (*expr_p), TREE_OPERAND (*expr_p, 0),
+	   integer_zero_node, TREE_TYPE (*expr_p))) != NULL_TREE)
     *expr_p = tem;
 
   /* If we still have a conversion at the toplevel,
@@ -2257,6 +2257,7 @@ gimplify_arg (tree *arg_p, gimple_seq *p
   /* If this is a variable sized type, we must remember the size.  */
   maybe_with_size_expr (arg_p);
 
+  /* FIXME diagnostics: This will mess up gcc.dg/Warray-bounds.c.  */
   /* Make sure arguments have the same location as the function call
      itself.  */
   protected_set_expr_location (*arg_p, call_location);
@@ -6741,8 +6742,9 @@ gimplify_expr (tree *expr_p, gimple_seq 
 	   */
 	  if (TREE_CODE (TREE_OPERAND (*expr_p, 1)) == INTEGER_CST
 	      && (tmp = maybe_fold_offset_to_address
-			 (TREE_OPERAND (*expr_p, 0), TREE_OPERAND (*expr_p, 1),
-		   	  TREE_TYPE (*expr_p))))
+		  (EXPR_LOCATION (*expr_p),
+		   TREE_OPERAND (*expr_p, 0), TREE_OPERAND (*expr_p, 1),
+		   TREE_TYPE (*expr_p))))
 	    {
 	      *expr_p = tmp;
 	      break;
@@ -6753,10 +6755,11 @@ gimplify_expr (tree *expr_p, gimple_seq 
 	      && POINTER_TYPE_P (TREE_TYPE (TREE_OPERAND (TREE_OPERAND (*expr_p,
 									0),0)))
 	      && (tmp = maybe_fold_offset_to_address
-			 (TREE_OPERAND (TREE_OPERAND (*expr_p, 0), 0),
-			  TREE_OPERAND (*expr_p, 1),
-		   	  TREE_TYPE (TREE_OPERAND (TREE_OPERAND (*expr_p, 0),
-						   0)))))
+		  (EXPR_LOCATION (*expr_p),
+		   TREE_OPERAND (TREE_OPERAND (*expr_p, 0), 0),
+		   TREE_OPERAND (*expr_p, 1),
+		   TREE_TYPE (TREE_OPERAND (TREE_OPERAND (*expr_p, 0),
+					    0)))))
 	     {
                *expr_p = fold_convert (TREE_TYPE (*expr_p), tmp);
 	       break;
Index: tree-ssa-forwprop.c
===================================================================
--- tree-ssa-forwprop.c	(revision 144319)
+++ tree-ssa-forwprop.c	(working copy)
@@ -828,7 +828,8 @@ forward_propagate_addr_expr_1 (tree name
      of the elements in X into &x[C/element size].  */
   if (TREE_CODE (rhs2) == INTEGER_CST)
     {
-      tree new_rhs = maybe_fold_stmt_addition (gimple_expr_type (use_stmt),
+      tree new_rhs = maybe_fold_stmt_addition (gimple_location (use_stmt),
+	  				       gimple_expr_type (use_stmt),
 					       array_ref, rhs2);
       if (new_rhs)
 	{
Index: common.opt
===================================================================
--- common.opt	(revision 144319)
+++ common.opt	(working copy)
@@ -1050,7 +1050,7 @@ Common Report Var(flag_see) Init(0)
 Eliminate redundant sign extensions using LCM.
 
 fshow-column
-Common C ObjC C++ ObjC++ Report Var(flag_show_column) Init(0)
+Common C ObjC C++ ObjC++ Report Var(flag_show_column) Init(1)
 Show column numbers in diagnostics, when available.  Default off
 
 fsignaling-nans
Index: c-omp.c
===================================================================
--- c-omp.c	(revision 144319)
+++ c-omp.c	(working copy)
@@ -151,7 +151,7 @@ c_finish_omp_atomic (location_t loc, enu
   /* There are lots of warnings, errors, and conversions that need to happen
      in the course of interpreting a statement.  Use the normal mechanisms
      to do this, and then take it apart again.  */
-  x = build_modify_expr (input_location, lhs, code, rhs);
+  x = build_modify_expr (input_location, lhs, code, input_location, rhs);
   if (x == error_mark_node)
     return error_mark_node;
   gcc_assert (TREE_CODE (x) == MODIFY_EXPR);  
@@ -273,7 +273,12 @@ c_finish_omp_for (location_t locus, tree
 	      fail = true;
 	    }
 
-	  init = build_modify_expr (elocus, decl, NOP_EXPR, init);
+	  init = build_modify_expr (elocus, decl, NOP_EXPR,
+				    /* FIXME diagnostics: This should
+				       be the location of the
+				       INIT.  */
+				    elocus,
+				    init);
 	}
       gcc_assert (TREE_CODE (init) == MODIFY_EXPR);
       gcc_assert (TREE_OPERAND (init, 0) == decl);
Index: ChangeLog.diagnostics
===================================================================
--- ChangeLog.diagnostics	(revision 144319)
+++ ChangeLog.diagnostics	(working copy)
@@ -1,3 +1,71 @@
+2009-03-05  Aldy Hernandez  <aldyh@redhat.com>
+
+	* common.opt (fshow-column): Enable by default.
+	* tree-vrp.c (check_array_ref): Use warning_at.
+	(check_array_bounds): Use location from call back if expr has no
+	location.
+	* tree.h: Add location argument to maybe_fold_*.
+	* tree-ssa-ccp.c (ccp_fold): Pass location to maybe_fold_*.
+	(maybe_fold_offset_to_array_ref): Add location argument and use it.
+	(maybe_fold_offset_to_component_ref): Same.
+	(maybe_fold_offset_to_reference): Same.
+	(maybe_fold_offset_to_address): Same.
+	(maybe_fold_stmt_indirect): Same.
+	(maybe_fold_stmt_addition): Same.
+	(fold_stmt_r): Pass location to maybe_fold_*.
+	(fold_gimple_assign): Same.
+	* c-tree.h: Add location argument to finish_decl,
+	default_function_array_conversion, store_init_value.
+	* c-decl.c (define_label): Use error_at.
+	(c_make_fname_decl): Pass location to finish_decl.
+	(finish_decl): New location argument.
+	(build_compound_literal): Pass location to store_init_value.
+	(grokdeclarator): Pass location to finish_decl.
+	(grokfield): Same.
+	* c-typeck.c (array_to_pointer_conversion): New location argument.
+	(function_to_pointer_conversion): Same.
+	(default_function_array_conversion): Same.
+	(parser_build_unary_op): Pass location to overflow_warning.
+	(parser_build_binary_op): Same.  Use warning_at.
+	(build_unary_op): Pass location to array_to_pointer_conversion.
+	(build_c_cast): Pass location to digest_init.
+	(build_modify_expr): New location argument.
+	(convert_for_assignment): Same.
+	(store_init_value): Same.
+	(digest_init): Same.
+	(output_init_element): Pass location to digest_init and
+	array_to_pointer_conversion.
+	(c_finish_return): Pass location to convert_for_assignment.
+	* gimplify.c (gimplify_conversion): Pass location to
+	maybe_fold_offset_to_address.
+	* tree-ssa-forwprop.c (forward_propagate_addr_expr_1): Pass location
+	to maybe_fold_stmt_addition.
+	* c-omp.c (c_finish_omp_atomic): Pass new location to
+	build_modify_expr.
+	(c_finish_omp_for): Same.
+	* c-common.c (overflow_warning): New argument.
+	* c-common.h: New argument to build_modify_expr, overflow_warning.
+	* c-parser.c (c_parser_declaration_or_fndef): Pass location to
+	finish_decl.
+	(c_parser_initializer): Pass location to
+	default_function_array_conversion.
+	(c_parser_initelt): Same.
+	(c_parser_initval): Same.
+	(c_parser_asm_operands): Same.
+	(c_parser_expr_no_commas): Same.  Pass location to build_modify_expr.
+	(c_parser_conditional_expression): Same.
+	(c_parser_binary_expression): Add location info to stack.  Use it.
+	(c_parser_unary_expression): Pass location to
+	default_function_array_conversion, parser_build_unary_op,
+	build_indirect_ref, c_parser_postfix_expression_after_primary.
+	(c_parser_postfix_expression_after_primary): New location argument.
+	Use it.
+	(c_parser_expression_conv): Pass location to
+	default_function_array_conversion.
+	(c_parser_expr_list): Same.
+	(c_parser_omp_atomic): Same.
+	(c_parser_omp_for_loop): Same.
+
 2009-02-11  Aldy Hernandez  <aldyh@redhat.com>
 
 	* c-tree.h: (struct c_declarator): Add comment to id_loc.
Index: c-common.c
===================================================================
--- c-common.c	(revision 144319)
+++ c-common.c	(working copy)
@@ -1147,33 +1147,36 @@ constant_expression_error (tree value)
    already overflowed.  */
 
 void
-overflow_warning (tree value)
+overflow_warning (location_t loc, tree value)
 {
   if (skip_evaluation) return;
 
   switch (TREE_CODE (value))
     {
     case INTEGER_CST:
-      warning (OPT_Woverflow, "integer overflow in expression");
+      warning_at (loc, OPT_Woverflow, "integer overflow in expression");
       break;
       
     case REAL_CST:
-      warning (OPT_Woverflow, "floating point overflow in expression");
+      warning_at (loc, OPT_Woverflow,
+		  "floating point overflow in expression");
       break;
       
     case FIXED_CST:
-      warning (OPT_Woverflow, "fixed-point overflow in expression");
+      warning_at (loc, OPT_Woverflow, "fixed-point overflow in expression");
       break;
 
     case VECTOR_CST:
-      warning (OPT_Woverflow, "vector overflow in expression");
+      warning_at (loc, OPT_Woverflow, "vector overflow in expression");
       break;
       
     case COMPLEX_CST:
       if (TREE_CODE (TREE_REALPART (value)) == INTEGER_CST)
-	warning (OPT_Woverflow, "complex integer overflow in expression");
+	warning_at (loc, OPT_Woverflow,
+		    "complex integer overflow in expression");
       else if (TREE_CODE (TREE_REALPART (value)) == REAL_CST)
-	warning (OPT_Woverflow, "complex floating point overflow in expression");
+	warning_at (loc, OPT_Woverflow,
+		    "complex floating point overflow in expression");
       break;
 
     default:
Index: c-common.h
===================================================================
--- c-common.h	(revision 144319)
+++ c-common.h	(working copy)
@@ -356,7 +356,8 @@ extern tree add_stmt (tree);
 extern void push_cleanup (tree, tree, bool);
 extern tree pushdecl_top_level (tree);
 extern tree pushdecl (tree);
-extern tree build_modify_expr (location_t, tree, enum tree_code, tree);
+extern tree build_modify_expr (location_t, tree, enum tree_code,
+			       location_t, tree);
 extern tree build_indirect_ref (location_t, tree, const char *);
 
 extern int c_expand_decl (tree);
@@ -728,7 +729,7 @@ extern void constant_expression_error (t
 extern bool strict_aliasing_warning (tree, tree, tree);
 extern void warnings_for_convert_and_check (tree, tree, tree);
 extern tree convert_and_check (tree, tree);
-extern void overflow_warning (tree);
+extern void overflow_warning (location_t, tree);
 extern void warn_logical_operator (enum tree_code, tree, tree);
 extern void check_main_parameter_types (tree decl);
 extern bool c_determine_visibility (tree);
Index: c-parser.c
===================================================================
--- c-parser.c	(revision 144319)
+++ c-parser.c	(working copy)
@@ -912,6 +912,7 @@ static struct c_expr c_parser_postfix_ex
 static struct c_expr c_parser_postfix_expression_after_paren_type (c_parser *,
 								   struct c_type_name *);
 static struct c_expr c_parser_postfix_expression_after_primary (c_parser *,
+								location_t loc,
 								struct c_expr);
 static struct c_expr c_parser_expression (c_parser *);
 static struct c_expr c_parser_expression_conv (c_parser *);
@@ -1216,6 +1217,7 @@ c_parser_declaration_or_fndef (c_parser 
 	    {
 	      tree d;
 	      struct c_expr init;
+	      location_t init_loc;
 	      c_parser_consume_token (parser);
 	      /* The declaration of the variable is in effect while
 		 its initializer is parsed.  */
@@ -1224,12 +1226,13 @@ c_parser_declaration_or_fndef (c_parser 
 	      if (!d)
 		d = error_mark_node;
 	      start_init (d, asm_name, global_bindings_p ());
+	      init_loc = c_parser_peek_token (parser)->location;
 	      init = c_parser_initializer (parser);
 	      finish_init ();
 	      if (d != error_mark_node)
 		{
 		  maybe_warn_string_init (TREE_TYPE (d), init);
-		  finish_decl (d, init.value, asm_name);
+		  finish_decl (d, init_loc, init.value, asm_name);
 		}
 	    }
 	  else
@@ -1238,7 +1241,7 @@ c_parser_declaration_or_fndef (c_parser 
 				   chainon (postfix_attrs,
 					    all_prefix_attrs));
 	      if (d)
-		finish_decl (d, NULL_TREE, asm_name);
+		finish_decl (d, UNKNOWN_LOCATION, NULL_TREE, asm_name);
 	    }
 	  if (c_parser_next_token_is (parser, CPP_COMMA))
 	    {
@@ -2988,10 +2991,11 @@ c_parser_initializer (c_parser *parser)
   else
     {
       struct c_expr ret;
+      location_t loc = c_parser_peek_token (parser)->location;
       ret = c_parser_expr_no_commas (parser, NULL);
       if (TREE_CODE (ret.value) != STRING_CST
 	  && TREE_CODE (ret.value) != COMPOUND_LITERAL_EXPR)
-	ret = default_function_array_conversion (ret);
+	ret = default_function_array_conversion (loc, ret);
       return ret;
     }
 }
@@ -3154,11 +3158,13 @@ c_parser_initelt (c_parser *parser)
 		  while (c_parser_next_token_is (parser, CPP_COMMA))
 		    {
 		      struct c_expr next;
-		      location_t loc = c_parser_peek_token (parser)->location;
+		      location_t comma_loc, exp_loc;
+		      comma_loc = c_parser_peek_token (parser)->location;
 		      c_parser_consume_token (parser);
+		      exp_loc = c_parser_peek_token (parser)->location;
 		      next = c_parser_expr_no_commas (parser, NULL);
-		      next = default_function_array_conversion (next);
-		      rec = build_compound_expr (loc, rec, next.value);
+		      next = default_function_array_conversion (exp_loc, next);
+		      rec = build_compound_expr (comma_loc, rec, next.value);
 		    }
 		parse_message_args:
 		  /* Now parse the objc-message-args.  */
@@ -3243,11 +3249,12 @@ c_parser_initval (c_parser *parser, stru
     init = c_parser_braced_init (parser, NULL_TREE, true);
   else
     {
+      location_t loc = c_parser_peek_token (parser)->location;
       init = c_parser_expr_no_commas (parser, after);
       if (init.value != NULL_TREE
 	  && TREE_CODE (init.value) != STRING_CST
 	  && TREE_CODE (init.value) != COMPOUND_LITERAL_EXPR)
-	init = default_function_array_conversion (init);
+	init = default_function_array_conversion (loc, init);
     }
   process_init_element (init, false);
 }
@@ -4285,6 +4292,7 @@ static tree
 c_parser_asm_operands (c_parser *parser, bool convert_p)
 {
   tree list = NULL_TREE;
+  location_t loc;
   while (true)
     {
       tree name, str;
@@ -4319,9 +4327,10 @@ c_parser_asm_operands (c_parser *parser,
 	  parser->lex_untranslated_string = true;
 	  return NULL_TREE;
 	}
+      loc = c_parser_peek_token (parser)->location;
       expr = c_parser_expression (parser);
       if (convert_p)
-	expr = default_function_array_conversion (expr);
+	expr = default_function_array_conversion (loc, expr);
       parser->lex_untranslated_string = true;
       if (!c_parser_require (parser, CPP_CLOSE_PAREN, "expected %<)%>"))
 	{
@@ -4385,7 +4394,7 @@ c_parser_expr_no_commas (c_parser *parse
 {
   struct c_expr lhs, rhs, ret;
   enum tree_code code;
-  location_t op_location;
+  location_t op_location, exp_location;
   gcc_assert (!after || c_dialect_objc ());
   lhs = c_parser_conditional_expression (parser, after);
   op_location = c_parser_peek_token (parser)->location;
@@ -4428,9 +4437,11 @@ c_parser_expr_no_commas (c_parser *parse
       return lhs;
     }
   c_parser_consume_token (parser);
+  exp_location = c_parser_peek_token (parser)->location;
   rhs = c_parser_expr_no_commas (parser, NULL);
-  rhs = default_function_array_conversion (rhs);
-  ret.value = build_modify_expr (op_location, lhs.value, code, rhs.value);
+  rhs = default_function_array_conversion (exp_location, rhs);
+  ret.value = build_modify_expr (op_location, lhs.value, code,
+				 exp_location, rhs.value);
   if (code == NOP_EXPR)
     ret.original_code = MODIFY_EXPR;
   else
@@ -4463,13 +4474,12 @@ c_parser_conditional_expression (c_parse
 
   gcc_assert (!after || c_dialect_objc ());
 
-  cond_loc = c_parser_peek_token (parser)->location;
   cond = c_parser_binary_expression (parser, after);
-  protected_set_expr_location (cond.value, cond_loc);
 
   if (c_parser_next_token_is_not (parser, CPP_QUERY))
     return cond;
-  cond = default_function_array_conversion (cond);
+  cond_loc = c_parser_peek_token (parser)->location;
+  cond = default_function_array_conversion (cond_loc, cond);
   c_parser_consume_token (parser);
   if (c_parser_next_token_is (parser, CPP_COLON))
     {
@@ -4497,8 +4507,11 @@ c_parser_conditional_expression (c_parse
       ret.original_code = ERROR_MARK;
       return ret;
     }
-  exp2 = c_parser_conditional_expression (parser, NULL);
-  exp2 = default_function_array_conversion (exp2);
+  {
+    location_t exp2_loc = c_parser_peek_token (parser)->location;
+    exp2 = c_parser_conditional_expression (parser, NULL);
+    exp2 = default_function_array_conversion (exp2_loc, exp2);
+  }
   skip_evaluation -= cond.value == truthvalue_true_node;
   ret.value = build_conditional_expr (cond_loc,
 				      cond.value, exp1.value, exp2.value);
@@ -4603,6 +4616,8 @@ c_parser_binary_expression (c_parser *pa
   struct {
     /* The expression at this stack level.  */
     struct c_expr expr;
+    /* The expression's location.  */
+    location_t loc;
     /* The precedence of the operator on its left, PREC_NONE at the
        bottom of the stack.  */
     enum prec prec;
@@ -4626,9 +4641,10 @@ c_parser_binary_expression (c_parser *pa
 	break;								      \
       }									      \
     stack[sp - 1].expr							      \
-      = default_function_array_conversion (stack[sp - 1].expr);		      \
+      = default_function_array_conversion (stack[sp - 1].loc,		      \
+					   stack[sp - 1].expr);		      \
     stack[sp].expr							      \
-      = default_function_array_conversion (stack[sp].expr);		      \
+      = default_function_array_conversion (stack[sp].loc, stack[sp].expr);    \
     stack[sp - 1].expr = parser_build_binary_op (binary_loc,		      \
 						 stack[sp].op,		      \
 						 stack[sp - 1].expr,	      \
@@ -4636,6 +4652,7 @@ c_parser_binary_expression (c_parser *pa
     sp--;								      \
   } while (0)
   gcc_assert (!after || c_dialect_objc ());
+  stack[0].loc = c_parser_peek_token (parser)->location;
   stack[0].expr = c_parser_cast_expression (parser, after);
   stack[0].prec = PREC_NONE;
   sp = 0;
@@ -4732,14 +4749,16 @@ c_parser_binary_expression (c_parser *pa
 	{
 	case TRUTH_ANDIF_EXPR:
 	  stack[sp].expr
-	    = default_function_array_conversion (stack[sp].expr);
+	    = default_function_array_conversion (stack[sp].loc,
+						 stack[sp].expr);
 	  stack[sp].expr.value = c_objc_common_truthvalue_conversion
 	    (binary_loc, default_conversion (stack[sp].expr.value));
 	  skip_evaluation += stack[sp].expr.value == truthvalue_false_node;
 	  break;
 	case TRUTH_ORIF_EXPR:
 	  stack[sp].expr
-	    = default_function_array_conversion (stack[sp].expr);
+	    = default_function_array_conversion (stack[sp].loc,
+						 stack[sp].expr);
 	  stack[sp].expr.value = c_objc_common_truthvalue_conversion
 	    (binary_loc, default_conversion (stack[sp].expr.value));
 	  skip_evaluation += stack[sp].expr.value == truthvalue_true_node;
@@ -4751,6 +4770,7 @@ c_parser_binary_expression (c_parser *pa
       stack[sp].expr = c_parser_cast_expression (parser, NULL);
       stack[sp].prec = oprec;
       stack[sp].op = ocode;
+      stack[sp].loc = binary_loc;
     }
  out:
   while (sp > 0)
@@ -4774,7 +4794,8 @@ c_parser_cast_expression (c_parser *pars
   location_t cast_loc = c_parser_peek_token (parser)->location;
   gcc_assert (!after || c_dialect_objc ());
   if (after)
-    return c_parser_postfix_expression_after_primary (parser, *after);
+    return c_parser_postfix_expression_after_primary (parser,
+						      cast_loc, *after);
   /* If the expression begins with a parenthesized type name, it may
      be either a cast or a compound literal; we need to see whether
      the next character is '{' to tell the difference.  If not, it is
@@ -4801,8 +4822,11 @@ c_parser_cast_expression (c_parser *pars
       if (c_parser_next_token_is (parser, CPP_OPEN_BRACE))
 	return c_parser_postfix_expression_after_paren_type (parser,
 							     type_name);
-      expr = c_parser_cast_expression (parser, NULL);
-      expr = default_function_array_conversion (expr);
+      {
+	location_t expr_loc = c_parser_peek_token (parser)->location;
+	expr = c_parser_cast_expression (parser, NULL);
+	expr = default_function_array_conversion (expr_loc, expr);
+      }
       ret.value = c_cast_expr (cast_loc, type_name, expr.value);
       ret.original_code = ERROR_MARK;
       return ret;
@@ -4843,61 +4867,69 @@ c_parser_unary_expression (c_parser *par
 {
   int ext;
   struct c_expr ret, op;
-  location_t loc = c_parser_peek_token (parser)->location;
+  location_t op_loc = c_parser_peek_token (parser)->location;
+  location_t exp_loc;
   switch (c_parser_peek_token (parser)->type)
     {
     case CPP_PLUS_PLUS:
       c_parser_consume_token (parser);
+      exp_loc = c_parser_peek_token (parser)->location;
       op = c_parser_cast_expression (parser, NULL);
-      op = default_function_array_conversion (op);
-      return parser_build_unary_op (loc, PREINCREMENT_EXPR, op);
+      op = default_function_array_conversion (exp_loc, op);
+      return parser_build_unary_op (op_loc, PREINCREMENT_EXPR, op);
     case CPP_MINUS_MINUS:
       c_parser_consume_token (parser);
+      exp_loc = c_parser_peek_token (parser)->location;
       op = c_parser_cast_expression (parser, NULL);
-      op = default_function_array_conversion (op);
-      return parser_build_unary_op (loc, PREDECREMENT_EXPR, op);
+      op = default_function_array_conversion (exp_loc, op);
+      return parser_build_unary_op (op_loc, PREDECREMENT_EXPR, op);
     case CPP_AND:
       c_parser_consume_token (parser);
-      return parser_build_unary_op (loc, ADDR_EXPR,
+      return parser_build_unary_op (op_loc, ADDR_EXPR,
 				    c_parser_cast_expression (parser, NULL));
     case CPP_MULT:
       c_parser_consume_token (parser);
+      exp_loc = c_parser_peek_token (parser)->location;
       op = c_parser_cast_expression (parser, NULL);
-      op = default_function_array_conversion (op);
-      ret.value = build_indirect_ref (loc, op.value, "unary *");
+      op = default_function_array_conversion (exp_loc, op);
+      ret.value = build_indirect_ref (op_loc, op.value, "unary *");
       ret.original_code = ERROR_MARK;
       return ret;
     case CPP_PLUS:
       if (!c_dialect_objc () && !in_system_header)
-	warning_at (c_parser_peek_token (parser)->location,
+	warning_at (op_loc,
 		    OPT_Wtraditional,
 		    "traditional C rejects the unary plus operator");
       c_parser_consume_token (parser);
+      exp_loc = c_parser_peek_token (parser)->location;
       op = c_parser_cast_expression (parser, NULL);
-      op = default_function_array_conversion (op);
-      return parser_build_unary_op (loc, CONVERT_EXPR, op);
+      op = default_function_array_conversion (exp_loc, op);
+      return parser_build_unary_op (op_loc, CONVERT_EXPR, op);
     case CPP_MINUS:
       c_parser_consume_token (parser);
+      exp_loc = c_parser_peek_token (parser)->location;
       op = c_parser_cast_expression (parser, NULL);
-      op = default_function_array_conversion (op);
-      return parser_build_unary_op (loc, NEGATE_EXPR, op);
+      op = default_function_array_conversion (exp_loc, op);
+      return parser_build_unary_op (op_loc, NEGATE_EXPR, op);
     case CPP_COMPL:
       c_parser_consume_token (parser);
+      exp_loc = c_parser_peek_token (parser)->location;
       op = c_parser_cast_expression (parser, NULL);
-      op = default_function_array_conversion (op);
-      return parser_build_unary_op (loc, BIT_NOT_EXPR, op);
+      op = default_function_array_conversion (exp_loc, op);
+      return parser_build_unary_op (op_loc, BIT_NOT_EXPR, op);
     case CPP_NOT:
       c_parser_consume_token (parser);
+      exp_loc = c_parser_peek_token (parser)->location;
       op = c_parser_cast_expression (parser, NULL);
-      op = default_function_array_conversion (op);
-      return parser_build_unary_op (loc, TRUTH_NOT_EXPR, op);
+      op = default_function_array_conversion (exp_loc, op);
+      return parser_build_unary_op (op_loc, TRUTH_NOT_EXPR, op);
     case CPP_AND_AND:
       /* Refer to the address of a label as a pointer.  */
       c_parser_consume_token (parser);
       if (c_parser_next_token_is (parser, CPP_NAME))
 	{
 	  ret.value = finish_label_address_expr
-	    (c_parser_peek_token (parser)->value, loc);
+	    (c_parser_peek_token (parser)->value, op_loc);
 	  c_parser_consume_token (parser);
 	}
       else
@@ -4922,14 +4954,16 @@ c_parser_unary_expression (c_parser *par
 	  return ret;
 	case RID_REALPART:
 	  c_parser_consume_token (parser);
+	  exp_loc = c_parser_peek_token (parser)->location;
 	  op = c_parser_cast_expression (parser, NULL);
-	  op = default_function_array_conversion (op);
-	  return parser_build_unary_op (loc, REALPART_EXPR, op);
+	  op = default_function_array_conversion (exp_loc, op);
+	  return parser_build_unary_op (op_loc, REALPART_EXPR, op);
 	case RID_IMAGPART:
 	  c_parser_consume_token (parser);
+	  exp_loc = c_parser_peek_token (parser)->location;
 	  op = c_parser_cast_expression (parser, NULL);
-	  op = default_function_array_conversion (op);
-	  return parser_build_unary_op (loc, IMAGPART_EXPR, op);
+	  op = default_function_array_conversion (exp_loc, op);
+	  return parser_build_unary_op (op_loc, IMAGPART_EXPR, op);
 	default:
 	  return c_parser_postfix_expression (parser);
 	}
@@ -5531,7 +5565,7 @@ c_parser_postfix_expression (c_parser *p
       expr.original_code = ERROR_MARK;
       break;
     }
-  return c_parser_postfix_expression_after_primary (parser, expr);
+  return c_parser_postfix_expression_after_primary (parser, loc, expr);
 }
 
 /* Parse a postfix expression after a parenthesized type name: the
@@ -5566,20 +5600,23 @@ c_parser_postfix_expression_after_paren_
     pedwarn (start_loc, OPT_pedantic, "ISO C90 forbids compound literals");
   expr.value = build_compound_literal (start_loc, type, init.value);
   expr.original_code = ERROR_MARK;
-  return c_parser_postfix_expression_after_primary (parser, expr);
+  return c_parser_postfix_expression_after_primary (parser, start_loc, expr);
 }
 
 /* Parse a postfix expression after the initial primary or compound
-   literal; that is, parse a series of postfix operators.  */
+   literal; that is, parse a series of postfix operators.
+
+   EXPR_LOC is the location of the primary expression.  */
 
 static struct c_expr
 c_parser_postfix_expression_after_primary (c_parser *parser,
+					   location_t expr_loc,
 					   struct c_expr expr)
 {
   tree ident, idx, exprlist;
-  location_t loc = c_parser_peek_token (parser)->location;
   while (true)
     {
+      location_t op_loc = c_parser_peek_token (parser)->location;
       switch (c_parser_peek_token (parser)->type)
 	{
 	case CPP_OPEN_SQUARE:
@@ -5588,7 +5625,7 @@ c_parser_postfix_expression_after_primar
 	  idx = c_parser_expression (parser).value;
 	  c_parser_skip_until_found (parser, CPP_CLOSE_SQUARE,
 				     "expected %<]%>");
-	  expr.value = build_array_ref (loc, expr.value, idx);
+	  expr.value = build_array_ref (op_loc, expr.value, idx);
 	  expr.original_code = ERROR_MARK;
 	  break;
 	case CPP_OPEN_PAREN:
@@ -5602,7 +5639,7 @@ c_parser_postfix_expression_after_primar
 				     "expected %<)%>");
 	  /* FIXME diagnostics: Ideally we want the FUNCNAME, not the
 	     "(" after the FUNCNAME, which is what we have now.    */
-	  expr.value = build_function_call (loc, expr.value, exprlist);
+	  expr.value = build_function_call (op_loc, expr.value, exprlist);
 	  expr.original_code = ERROR_MARK;
           if (warn_disallowed_functions)
             warn_if_disallowed_function_p (expr.value);
@@ -5610,7 +5647,7 @@ c_parser_postfix_expression_after_primar
 	case CPP_DOT:
 	  /* Structure element reference.  */
 	  c_parser_consume_token (parser);
-	  expr = default_function_array_conversion (expr);
+	  expr = default_function_array_conversion (expr_loc, expr);
 	  if (c_parser_next_token_is (parser, CPP_NAME))
 	    ident = c_parser_peek_token (parser)->value;
 	  else
@@ -5621,13 +5658,13 @@ c_parser_postfix_expression_after_primar
 	      return expr;
 	    }
 	  c_parser_consume_token (parser);
-	  expr.value = build_component_ref (loc, expr.value, ident);
+	  expr.value = build_component_ref (op_loc, expr.value, ident);
 	  expr.original_code = ERROR_MARK;
 	  break;
 	case CPP_DEREF:
 	  /* Structure element reference.  */
 	  c_parser_consume_token (parser);
-	  expr = default_function_array_conversion (expr);
+	  expr = default_function_array_conversion (expr_loc, expr);
 	  if (c_parser_next_token_is (parser, CPP_NAME))
 	    ident = c_parser_peek_token (parser)->value;
 	  else
@@ -5638,8 +5675,8 @@ c_parser_postfix_expression_after_primar
 	      return expr;
 	    }
 	  c_parser_consume_token (parser);
-	  expr.value = build_component_ref (loc,
-					    build_indirect_ref (loc,
+	  expr.value = build_component_ref (op_loc,
+					    build_indirect_ref (op_loc,
 								expr.value,
 								"->"),
 					    ident);
@@ -5648,16 +5685,16 @@ c_parser_postfix_expression_after_primar
 	case CPP_PLUS_PLUS:
 	  /* Postincrement.  */
 	  c_parser_consume_token (parser);
-	  expr = default_function_array_conversion (expr);
-	  expr.value = build_unary_op (loc,
+	  expr = default_function_array_conversion (expr_loc, expr);
+	  expr.value = build_unary_op (op_loc,
 				       POSTINCREMENT_EXPR, expr.value, 0);
 	  expr.original_code = ERROR_MARK;
 	  break;
 	case CPP_MINUS_MINUS:
 	  /* Postdecrement.  */
 	  c_parser_consume_token (parser);
-	  expr = default_function_array_conversion (expr);
-	  expr.value = build_unary_op (loc,
+	  expr = default_function_array_conversion (expr_loc, expr);
+	  expr.value = build_unary_op (op_loc,
 				       POSTDECREMENT_EXPR, expr.value, 0);
 	  expr.original_code = ERROR_MARK;
 	  break;
@@ -5683,9 +5720,11 @@ c_parser_expression (c_parser *parser)
     {
       struct c_expr next;
       location_t loc = c_parser_peek_token (parser)->location;
+      location_t expr_loc;
       c_parser_consume_token (parser);
+      expr_loc = c_parser_peek_token (parser)->location;
       next = c_parser_expr_no_commas (parser, NULL);
-      next = default_function_array_conversion (next);
+      next = default_function_array_conversion (expr_loc, next);
       expr.value = build_compound_expr (loc, expr.value, next.value);
       expr.original_code = COMPOUND_EXPR;
     }
@@ -5699,8 +5738,9 @@ static struct c_expr
 c_parser_expression_conv (c_parser *parser)
 {
   struct c_expr expr;
+  location_t loc = c_parser_peek_token (parser)->location;
   expr = c_parser_expression (parser);
-  expr = default_function_array_conversion (expr);
+  expr = default_function_array_conversion (loc, expr);
   return expr;
 }
 
@@ -5717,16 +5757,18 @@ c_parser_expr_list (c_parser *parser, bo
 {
   struct c_expr expr;
   tree ret, cur;
+  location_t loc = c_parser_peek_token (parser)->location;
   expr = c_parser_expr_no_commas (parser, NULL);
   if (convert_p)
-    expr = default_function_array_conversion (expr);
+    expr = default_function_array_conversion (loc, expr);
   ret = cur = build_tree_list (NULL_TREE, expr.value);
   while (c_parser_next_token_is (parser, CPP_COMMA))
     {
       c_parser_consume_token (parser);
+      loc = c_parser_peek_token (parser)->location;
       expr = c_parser_expr_no_commas (parser, NULL);
       if (convert_p)
-	expr = default_function_array_conversion (expr);
+	expr = default_function_array_conversion (loc, expr);
       cur = TREE_CHAIN (cur) = build_tree_list (NULL_TREE, expr.value);
     }
   return ret;
@@ -7534,8 +7576,11 @@ c_parser_omp_atomic (location_t loc, c_p
 	}
 
       c_parser_consume_token (parser);
-      rhs_expr = c_parser_expression (parser);
-      rhs_expr = default_function_array_conversion (rhs_expr);
+      {
+	location_t rhs_loc = c_parser_peek_token (parser)->location;
+	rhs_expr = c_parser_expression (parser);
+	rhs_expr = default_function_array_conversion (rhs_loc, rhs_expr);
+      }
       rhs = rhs_expr.value;
       break;
     }
@@ -7674,12 +7719,12 @@ c_parser_omp_for_loop (location_t loc,
 	  decl = c_parser_postfix_expression (parser).value;
 
 	  c_parser_require (parser, CPP_EQ, "expected %<=%>");
-	  init_loc = c_parser_peek_token (parser)->location;
 
+	  init_loc = c_parser_peek_token (parser)->location;
 	  init_exp = c_parser_expr_no_commas (parser, NULL);
-	  init_exp = default_function_array_conversion (init_exp);
+	  init_exp = default_function_array_conversion (init_loc, init_exp);
 	  init = build_modify_expr (init_loc,
-				    decl, NOP_EXPR, init_exp.value);
+				    decl, NOP_EXPR, init_loc, init_exp.value);
 	  init = c_process_expr_stmt (init_loc, init);
 
 	  c_parser_skip_until_found (parser, CPP_SEMICOLON, "expected %<;%>");


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]