https://gcc.gnu.org/bugzilla/show_bug.cgi?id=88677
Richard Biener <rguenth at gcc dot gnu.org> changed: What |Removed |Added ---------------------------------------------------------------------------- Keywords| |wrong-code Status|ASSIGNED |NEW CC| |rguenth at gcc dot gnu.org Assignee|rguenth at gcc dot gnu.org |hubicka at gcc dot gnu.org --- Comment #8 from Richard Biener <rguenth at gcc dot gnu.org> --- Value numbering stmt = SR.10_27 = MEM[(struct D *)&m]; -Setting value number of SR.10_27 to SR.10_27 (changed) +Setting value number of SR.10_27 to SR.9_23 (changed) but then of course the code-difference <bb 7> : - # SR.10_12 = PHI <0(5), SR.10_27(6)> return; is somewhat spurious since nothing uses SR.10_12, we're getting to removal only because eliding SR.10_27 enables DCE. <bb 6> : SR.10_27 = MEM[(struct D *)&m]; <bb 7> : # SR.10_12 = PHI <0(5), SR.10_27(6)> return; So the code-gen difference is likely because of the following which makes dropping TYPE_NEEDS_CONSTRUCTING a suspicious change. /* Return true if VAR may be aliased. A variable is considered as maybe aliased if it has its address taken by the local TU or possibly by another TU and might be modified through a pointer. */ static inline bool may_be_aliased (const_tree var) { return (TREE_CODE (var) != CONST_DECL && (TREE_PUBLIC (var) || DECL_EXTERNAL (var) || TREE_ADDRESSABLE (var)) && !((TREE_STATIC (var) || TREE_PUBLIC (var) || DECL_EXTERNAL (var)) && ((TREE_READONLY (var) && !TYPE_NEEDS_CONSTRUCTING (TREE_TYPE (var))) || (TREE_CODE (var) == VAR_DECL && DECL_NONALIASED (var))))); } the variable in question is <var_decl 0x7ffff7fefcf0 m type <record_type 0x7ffff69e6a80 D readonly needs-constructing type_1 type_5 SI size <integer_cst 0x7ffff689c078 constant 32> unit-size <integer_cst 0x7ffff689c090 constant 4> align:32 warn_if_not_align:0 symtab:0 alias-set -1 canonical-type 0x7ffff69e6a80 fields <function_decl 0x7ffff69f5c00 __ct type <method_type 0x7ffff69f3000> public abstract external autoinline decl_3 QI t.ii:2:29 align:16 warn_if_not_align:0 context <record_type 0x7ffff69e69d8 D> full-name "constexpr D<j>::D(D<j>&&) noexcept (<uninstantiated>)" not-really-extern chain <function_decl 0x7ffff69f5e00 __ct_base >> context <translation_unit_decl 0x7ffff6887168 t.ii> full-name "const class D<j>" needs-constructor X(constX&) this=(X&) n_parents=1 use_template=1 interface-unknown pointer_to_this <pointer_type 0x7ffff69f30a8> reference_to_this <reference_type 0x7ffff69f3150>> readonly addressable used public external read decl_2 VOID t.ii:17:19 align:8 warn_if_not_align:0 context <translation_unit_decl 0x7ffff6887168 t.ii> chain <type_decl 0x7ffff699cc78 j>> may_be_aliased tries to avoid claiming R/O data can be written to, but of course that's not true for the global ctor. -> You can't simply remove this flag. You could set it to true conservatively. Or we could stop marking globals that need constructing TREE_READONLY.