From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 2153) id CCC8A3888C7F; Sat, 19 Mar 2022 07:42:32 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org CCC8A3888C7F MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Content-Type: text/plain; charset="utf-8" From: Jakub Jelinek To: gcc-cvs@gcc.gnu.org Subject: [gcc r12-7720] c-family: Fix up ICE during pretty-printing of PMF related expression [PR101515] X-Act-Checkin: gcc X-Git-Author: Jakub Jelinek X-Git-Refname: refs/heads/master X-Git-Oldrev: 8ca61ad148ffedaae1914741c78dfd13962aab92 X-Git-Newrev: 2663d18356b0a62f5a800c7e5596d814cd3c2c41 Message-Id: <20220319074232.CCC8A3888C7F@sourceware.org> Date: Sat, 19 Mar 2022 07:42:32 +0000 (GMT) X-BeenThere: gcc-cvs@gcc.gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: Gcc-cvs mailing list List-Unsubscribe: , List-Archive: List-Help: List-Subscribe: , X-List-Received-Date: Sat, 19 Mar 2022 07:42:32 -0000 https://gcc.gnu.org/g:2663d18356b0a62f5a800c7e5596d814cd3c2c41 commit r12-7720-g2663d18356b0a62f5a800c7e5596d814cd3c2c41 Author: Jakub Jelinek Date: Sat Mar 19 08:40:47 2022 +0100 c-family: Fix up ICE during pretty-printing of PMF related expression [PR101515] The intent of r11-6729 is that it prints something that helps user to figure out what exactly is being accessed. When we find a unique non-static data member that is being accessed, even when we can't fold it nicely, IMNSHO it is better to print ((sometype *)&var)->field or (*(sometype *)&var).field instead of *(fieldtype *)((char *)&var + 56) because the user doesn't know what is at offset 56, we shouldn't ask user to decipher structure layout etc. One question is if we could return something better for the TYPE_PTRMEMFUNC_FLAG RECORD_TYPE members here (something that would print it more naturally/readably in a C++ way), though the fact that the routine is in c-family makes it harder. Another one is whether we shouldn't punt for FIELD_DECLs that don't have nicely printable name of its containing scope, something like: if (tree scope = get_containing_scope (field)) if (TYPE_P (scope) && TYPE_NAME (scope) == NULL_TREE) break; return cop; or so. This patch implements that. Note the returned cop is a COMPONENT_REF where the first argument has a nicely printable type name (x with type sp), but sp's TYPE_MAIN_VARIANT is the unnamed TYPE_PTRMEMFUNC_FLAG. So another possibility would be if we see such a problem for the FIELD_DECL's scope, check if TYPE_MAIN_VARIANT of the first COMPONENT_REF's argument is equal to that scope and in that case use TREE_TYPE of the first COMPONENT_REF's argument as the scope instead. 2022-03-19 Jakub Jelinek PR c++/101515 * c-pretty-print.cc (c_fold_indirect_ref_for_warn): For C++ don't return COMPONENT_REFs with FIELD_DECLs whose containing scope can't be printed. * g++.dg/warn/pr101515.C: New test. Diff: --- gcc/c-family/c-pretty-print.cc | 6 ++++++ gcc/testsuite/g++.dg/warn/pr101515.C | 18 ++++++++++++++++++ 2 files changed, 24 insertions(+) diff --git a/gcc/c-family/c-pretty-print.cc b/gcc/c-family/c-pretty-print.cc index dac17753acb..71a0cb51093 100644 --- a/gcc/c-family/c-pretty-print.cc +++ b/gcc/c-family/c-pretty-print.cc @@ -1889,6 +1889,12 @@ c_fold_indirect_ref_for_warn (location_t loc, tree type, tree op, = wi::to_offset (TYPE_SIZE_UNIT (TREE_TYPE (field))); if (upos <= off && off < upos + el_sz) { + /* The C++ pretty printers print scope of the FIELD_DECLs, + so punt if it is something that can't be printed. */ + if (c_dialect_cxx ()) + if (tree scope = get_containing_scope (field)) + if (TYPE_P (scope) && TYPE_NAME (scope) == NULL_TREE) + break; tree cop = build3_loc (loc, COMPONENT_REF, TREE_TYPE (field), op, field, NULL_TREE); off = off - upos; diff --git a/gcc/testsuite/g++.dg/warn/pr101515.C b/gcc/testsuite/g++.dg/warn/pr101515.C new file mode 100644 index 00000000000..f3c58b89094 --- /dev/null +++ b/gcc/testsuite/g++.dg/warn/pr101515.C @@ -0,0 +1,18 @@ +// PR c++/101515 +// { dg-do compile } +// { dg-options "-O1 -Wuninitialized" } + +struct S { int j; }; +struct T : public S { virtual void h () {} }; +struct U { void (*ptr) (); }; +typedef void (S::*sp) (); + +int +main () +{ + T t; + sp x; + U *xp = (U *) &x; + if (xp->ptr != ((void (*) ()) (sizeof (void *)))) // { dg-warning "is used uninitialized" } + return 1; +}