[Bug c++/124973] [16 regression] ICE w/ modules, constexpr, and O[1-3]

cvs-commit at gcc dot gnu.org gcc-bugzilla@gcc.gnu.org
Thu Apr 23 01:15:43 GMT 2026


https://gcc.gnu.org/bugzilla/show_bug.cgi?id=124973

--- Comment #3 from GCC Commits <cvs-commit at gcc dot gnu.org> ---
The releases/gcc-16 branch has been updated by Jason Merrill
<jason@gcc.gnu.org>:

https://gcc.gnu.org/g:663d3839eab135ebadf6a14578d46c3c77d85585

commit r16-8808-g663d3839eab135ebadf6a14578d46c3c77d85585
Author: Jason Merrill <jason@redhat.com>
Date:   Wed Apr 22 21:15:18 2026 -0400

    c++: consteval, array, modules [PR124973]

    Here the consteval holder constructor calls the defaulted element_array
    constructor, which uses a VEC_INIT_EXPR to call the defaulted element
    constructor.

    When we read in the holder constructor, we need to clone it, so we call
    finish_function, which calls cp_fold_function_non_odr_use, which tries to
    constant-evaluate the call to the element_array constructor.  This
    eventually wants to evaluate the VEC_INIT_EXPR, which wants to call the
    element constructor (complete object clone).  But we haven't cloned the
    element constructor yet, so mark_used tries to synthesize it again, which
    breaks because the constructor is already defined, just not cloned yet.

    We should have cloned the element constructor first, but we didn't know
that
    the element_array constructor depends on it because VEC_INIT_EXPR doesn't
    express that; build_vec_init_expr calls build_vec_init_elt and then throws
    it away.  Perhaps we want to add the elt_init as an additional operand that
    is used to express dependencies, but ignored in expansion?

    It would also be nice not to repeat all the finish_function passes when
    loading a function from a module; we already did
    cp_fold_function_non_odr_use and such for this function before writing out
    the module, doing it again is a waste of time.

    But also, trying to constant-evaluate the element_array constructor is
wrong
    for _non_odr_use, it shouldn't be doing any optimization folding.

    Furthermore, since the TARGET_EXPR is wrapped in an INIT_EXPR, we should
    never have tried to fold it by itself, before cp_genericize_init_expr has a
    chance to elide it.  So let's only do that folding when ff_genericize, like
    the other TARGET_EXPR transformations.  This is a much simpler fix for this
    testcase.

    While we're at it, let's also suppress the other flag_no_inline-conditional
    folding when ff_only_non_odr.

            PR c++/124973
            PR c++/120502
            PR c++/120005

    gcc/cp/ChangeLog:

            * cp-gimplify.cc (cp_fold_r) <case TARGET_EXPR>: Only
            do optimization folding when ff_genericize.
            (cp_fold) <case CALL_EXPR>: Don't do
            optimization folding when ff_only_non_odr.

    gcc/testsuite/ChangeLog:

            * g++.dg/modules/consteval-1_a.C: New test.
            * g++.dg/modules/consteval-1_b.C: New test.

    (cherry picked from commit b6e40cf38c60d11c4e105f9179a6d5cfb502bd9b)


More information about the Gcc-bugs mailing list