This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[PATCH 06/17] C: use BLT to highlight parameter of callee decl for mismatching types
- From: David Malcolm <dmalcolm at redhat dot com>
- To: gcc-patches at gcc dot gnu dot org
- Cc: David Malcolm <dmalcolm at redhat dot com>
- Date: Mon, 24 Jul 2017 16:05:03 -0400
- Subject: [PATCH 06/17] C: use BLT to highlight parameter of callee decl for mismatching types
- Authentication-results: sourceware.org; auth=none
- Authentication-results: ext-mx07.extmail.prod.ext.phx2.redhat.com; dmarc=none (p=none dis=none) header.from=redhat.com
- Authentication-results: ext-mx07.extmail.prod.ext.phx2.redhat.com; spf=pass smtp.mailfrom=dmalcolm at redhat dot com
- Dkim-filter: OpenDKIM Filter v2.11.0 mx1.redhat.com B7B40C1EA9E9
- Dmarc-filter: OpenDMARC Filter v1.3.2 mx1.redhat.com B7B40C1EA9E9
- References: <1500926714-56988-1-git-send-email-dmalcolm@redhat.com>
This patch to the C frontend uses the BLT infrastructure to improve:
extern int callee_1 (int one, const char *two, float three);
int test_1 (int first, int second, float third)
{
return callee_1 (first, second, third);
}
from:
warning: passing argument 2 of 'callee_1' makes pointer from integer without a cast [-Wint-conversion]
return callee_1 (first, second, third);
^~~~~~
note: expected 'const char *' but argument is of type 'int'
extern int callee_1 (int one, const char *two, float three);
^~~~~~~~
to:
warning: passing argument 2 of 'callee_1' makes pointer from integer without a cast [-Wint-conversion]
return callee_1 (first, second, third);
^~~~~~
note: expected 'const char *' but argument is of type 'int'
extern int callee_1 (int one, const char *two, float three);
^~~~~~~~~~~~~~~
by locating the pertinent parameter within the decl, by traversing the
BLT tree (if present).
gcc/c/ChangeLog:
* c-typeck.c: Include "blt.h".
(get_fndecl_argument_location): New function.
(convert_for_assignment): Replace calls to "inform" with...
(inform_for_arg): ...this new function, attempting to highlight
the pertinent parameter.
gcc/testsuite/ChangeLog:
* gcc.dg/param-type-mismatch.c: Add -fblt to options. Update
expected underlining to show the pertinent parameters.
---
gcc/c/c-typeck.c | 63 ++++++++++++++++++++++++------
gcc/testsuite/gcc.dg/param-type-mismatch.c | 13 +++---
2 files changed, 56 insertions(+), 20 deletions(-)
diff --git a/gcc/c/c-typeck.c b/gcc/c/c-typeck.c
index 4d067e9..c37cc33 100644
--- a/gcc/c/c-typeck.c
+++ b/gcc/c/c-typeck.c
@@ -51,6 +51,7 @@ along with GCC; see the file COPYING3. If not see
#include "spellcheck-tree.h"
#include "gcc-rich-location.h"
#include "asan.h"
+#include "blt.h"
/* Possible cases of implicit bad conversions. Used to select
diagnostic messages in convert_for_assignment. */
@@ -6112,6 +6113,53 @@ maybe_warn_string_init (location_t loc, tree type, struct c_expr expr)
"array initialized from parenthesized string constant");
}
+/* Attempt to locate the parameter with the given index within FNDECL,
+ returning LOC if it can't be found (or blt was not enabled). */
+
+static location_t
+get_fndecl_argument_location (tree fundecl, int argnum, location_t loc)
+{
+ blt_node *node = blt_get_node_for_tree (fundecl);
+ if (!node)
+ return loc;
+
+ if (node->get_kind () != BLT_DIRECT_DECLARATOR)
+ return loc;
+
+ /* We expect a parameter-list containing parameter-declaration. */
+ node = node->get_first_child_of_kind (BLT_PARAMETER_LIST);
+ if (!node)
+ return loc;
+
+ auto_vec<blt_node *> params;
+ node->get_children_of_kind (params, BLT_PARAMETER_DECLARATION);
+
+ if (argnum >= (int)params.length ())
+ return loc;
+
+ blt_node *param = params[argnum];
+ return param->get_range ();
+}
+
+/* Issue a note about a mismatching argument for parameter PARMNUM
+ to FUNDECL, for types EXPECTED_TYPE and ACTUAL_TYPE.
+ Attempt to issue the note at the pertinent parameter of the decl;
+ failing that issue it at the location of FUNDECL; failing that
+ issue it at PLOC. */
+
+static void
+inform_for_arg (tree fundecl, location_t ploc, int parmnum,
+ tree expected_type, tree actual_type)
+{
+ location_t loc = (fundecl && !DECL_IS_BUILTIN (fundecl)
+ ? DECL_SOURCE_LOCATION (fundecl) : ploc);
+ loc = get_fndecl_argument_location (fundecl, parmnum - 1, loc);
+
+ inform (loc,
+ "expected %qT but argument is of type %qT",
+ expected_type, actual_type);
+}
+
/* Convert value RHS to type TYPE as preparation for an assignment to
an lvalue of type TYPE. If ORIGTYPE is not NULL_TREE, it is the
original type of RHS; this differs from TREE_TYPE (RHS) for enum
@@ -6183,10 +6231,7 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type,
{ \
case ic_argpass: \
if (pedwarn (PLOC, OPT, AR, parmnum, rname)) \
- inform ((fundecl && !DECL_IS_BUILTIN (fundecl)) \
- ? DECL_SOURCE_LOCATION (fundecl) : PLOC, \
- "expected %qT but argument is of type %qT", \
- type, rhstype); \
+ inform_for_arg (fundecl, (PLOC), parmnum, type, rhstype); \
break; \
case ic_assign: \
pedwarn (LOCATION, OPT, AS); \
@@ -6212,10 +6257,7 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type,
{ \
case ic_argpass: \
if (pedwarn (PLOC, OPT, AR, parmnum, rname, QUALS)) \
- inform ((fundecl && !DECL_IS_BUILTIN (fundecl)) \
- ? DECL_SOURCE_LOCATION (fundecl) : PLOC, \
- "expected %qT but argument is of type %qT", \
- type, rhstype); \
+ inform_for_arg (fundecl, (PLOC), parmnum, type, rhstype); \
break; \
case ic_assign: \
pedwarn (LOCATION, OPT, AS, QUALS); \
@@ -6241,10 +6283,7 @@ convert_for_assignment (location_t location, location_t expr_loc, tree type,
{ \
case ic_argpass: \
if (warning_at (PLOC, OPT, AR, parmnum, rname, QUALS)) \
- inform ((fundecl && !DECL_IS_BUILTIN (fundecl)) \
- ? DECL_SOURCE_LOCATION (fundecl) : PLOC, \
- "expected %qT but argument is of type %qT", \
- type, rhstype); \
+ inform_for_arg (fundecl, (PLOC), parmnum, type, rhstype); \
break; \
case ic_assign: \
warning_at (LOCATION, OPT, AS, QUALS); \
diff --git a/gcc/testsuite/gcc.dg/param-type-mismatch.c b/gcc/testsuite/gcc.dg/param-type-mismatch.c
index 70ea0bc..eb3169b 100644
--- a/gcc/testsuite/gcc.dg/param-type-mismatch.c
+++ b/gcc/testsuite/gcc.dg/param-type-mismatch.c
@@ -1,9 +1,6 @@
-/* { dg-options "-fdiagnostics-show-caret" } */
+/* { dg-options "-fdiagnostics-show-caret -fblt" } */
-/* A collection of calls where argument 2 is of the wrong type.
-
- TODO: we should highlight the second parameter of the callee, rather
- than its name. */
+/* A collection of calls where argument 2 is of the wrong type. */
/* decl, with argname. */
@@ -19,7 +16,7 @@ int test_1 (int first, int second, float third)
/* { dg-message "expected 'const char \\*' but argument is of type 'int'" "" { target *-*-* } callee_1 } */
/* { dg-begin-multiline-output "" }
extern int callee_1 (int one, const char *two, float three);
- ^~~~~~~~
+ ^~~~~~~~~~~~~~~
{ dg-end-multiline-output "" } */
}
@@ -37,7 +34,7 @@ int test_2 (int first, int second, float third)
/* { dg-message "expected 'const char \\*' but argument is of type 'int'" "" { target *-*-* } callee_2 } */
/* { dg-begin-multiline-output "" }
extern int callee_2 (int, const char *, float);
- ^~~~~~~~
+ ^~~~~~~~~~~~
{ dg-end-multiline-output "" } */
}
@@ -58,6 +55,6 @@ int test_3 (int first, int second, float third)
/* { dg-message "expected 'const char \\*' but argument is of type 'int'" "" { target *-*-* } callee_3 } */
/* { dg-begin-multiline-output "" }
static int callee_3 (int one, const char *two, float three)
- ^~~~~~~~
+ ^~~~~~~~~~~~~~~
{ dg-end-multiline-output "" } */
}
--
1.8.5.3