[PATCH] Fix constexpr evaluation of comparisons involving pointer-to-members
Patrick Palka
patrick@parcs.ath.cx
Thu Feb 4 17:25:00 GMT 2016
On Thu, Feb 4, 2016 at 11:57 AM, Jason Merrill <jason@redhat.com> wrote:
> On 02/04/2016 10:32 AM, Patrick Palka wrote:
>>
>> On Thu, Feb 4, 2016 at 9:24 AM, Jason Merrill <jason@redhat.com> wrote:
>>>
>>> On 02/03/2016 12:51 PM, Patrick Palka wrote:
>>>>
>>>>
>>>> + && (integer_minus_onep (lhs)
>>>> + || integer_minus_onep (rhs)))
>>>
>>>
>>>
>>> Let's use null_member_pointer_value_p here.
>>
>>
>> Done.
>>
>>>
>>> Please add pointers to member functions to the testcase.
>>
>>
>> This does not currently work properly because comparisons between
>> distinct pointers to (non-virtual) member functions eventually perform
>> a comparison between two distinct FUNCTION_DECLs, and fold_binary_loc
>> currently does not fold away such comparisons. So any static_asserts
>> that perform comparisons between distinct function pointers or between
>> distinct pointers to (non-virtual) member functions fail with
>> "non-constant condition for static assertion". (Comparisons between
>> pointers to distinct virtual member functions _do_ work because in
>> that case we are ultimately just comparing integer offsets, not
>> FUNCTION_DECLs. And comparisons between equivalent pointers trivially
>> work.)
>>
>> I think the problem may lie in symtab_node::equal_address_to, which
>> apparently returns -1, instead of 0, for two obviously distinct
>> FUNCTION_DECLs.
>
>
> Right, because they might be defined as aliases elsewhere. But it looks
> like it should work if you define f and g.
That makes sense. But even when I define f and g, the comparisons
don't get folded away:
#define SA(x) static_assert ((x), #x)
void f () { }
void g () { }
struct X { int a, b; void f (); void g (); };
void X::f () { }
void X::g () { }
void
foo ()
{
SA (&f != &g);
SA (&X::f != &X::g);
}
bool bar = &f != &g;
Although the static_asserts fail, the initialization of the variable
bar _does_ get folded to 1 during gimplification. When evaluating the
static_asserts, symtab_node::equal_address_to again returns -1 but
during gimplification the same call to symtab_node::equal_address_to
returns 0. So probably the symbols are not fully defined yet in the
symbol table at the point when we are evaluating the static_asserts.
More information about the Gcc-patches
mailing list