https://gcc.gnu.org/bugzilla/show_bug.cgi?id=101502
Bug ID: 101502 Summary: Inconsistent behavior in maybe_record_node() Product: gcc Version: unknown Status: UNCONFIRMED Severity: normal Priority: P3 Component: ipa Assignee: unassigned at gcc dot gnu.org Reporter: fxue at os dot amperecomputing.com CC: marxin at gcc dot gnu.org Target Milestone: --- For code snippet in maybe_record_node(), behavior might be inconsistent when SANITIZE_UNREACHABLE is turned on. Suppose we are adding two functions (method_fn/__cxa_pure_virtual), content of nodes is order-sensitive. o. method_fn, __cxa_pure_virtual -> nodes: [ method_fn ] o. __cxa_pure_virtual, method_fn -> nodes: [ __cxa_pure_virtual, method_fn ] BTW: assertion on target_node->real_symbol_p() is redundant, since the condition is contained. else if (target_node != NULL && (TREE_PUBLIC (target) || DECL_EXTERNAL (target) || target_node->definition) && target_node->real_symbol_p ()) { gcc_assert (!target_node->inlined_to); gcc_assert (target_node->real_symbol_p ()); /* When sanitizing, do not assume that __cxa_pure_virtual is not called by valid program. */ if (flag_sanitize & SANITIZE_UNREACHABLE) ; /* Only add pure virtual if it is the only possible target. This way we will preserve the diagnostics about pure virtual called in many cases without disabling optimization in other. */ else if (pure_virtual) { if (nodes.length ()) return; } /* If we found a real target, take away cxa_pure_virtual. */ else if (!pure_virtual && nodes.length () == 1 && is_cxa_pure_virtual_p (nodes[0]->decl)) nodes.pop (); if (pure_virtual && nodes.length ()) return; if (!inserted->add (target)) { cached_polymorphic_call_targets->add (target_node); nodes.safe_push (target_node); } }