1 // RUN: %clang_cc1 -std=c++2a -verify %s
3 // ... return type shall be cv bool ...
7 double operator==(X
, Y
); // expected-note 4{{here}}
9 bool b
= y
== x
; // expected-error {{return type 'double' of selected 'operator==' function for rewritten '==' comparison is not 'bool'}}
10 bool c
= x
!= y
; // expected-error {{return type 'double' of selected 'operator==' function for rewritten '!=' comparison is not 'bool'}}
11 bool d
= y
!= x
; // expected-error {{return type 'double' of selected 'operator==' function for rewritten '!=' comparison is not 'bool'}}
13 // cv-qualifiers are OK
14 const bool operator==(Y
, X
);
15 bool e
= y
!= x
; // ok
17 // We don't prefer a function with bool return type over one witn non-bool return type.
18 bool f
= x
!= y
; // expected-error {{return type 'double' of selected 'operator==' function for rewritten '!=' comparison is not 'bool'}}
20 // As an extension, we permit integral and unscoped enumeration types too.
21 // These are used by popular C++ libraries such as ICU.
23 int operator==(X
, Z
); // expected-note {{here}}
24 bool g
= z
== x
; // expected-warning {{ISO C++20 requires return type of selected 'operator==' function for rewritten '==' comparison to be 'bool', not 'int'}}
27 E
operator==(Y
, Z
); // expected-note {{here}}
28 bool h
= z
== y
; // expected-warning {{ISO C++20 requires return type of selected 'operator==' function for rewritten '==' comparison to be 'bool', not 'E'}}
31 struct X
{ bool equal
; };
33 constexpr bool operator==(X x
, Y
) { return x
.equal
; }
35 static_assert(X
{true} == Y
{});
36 static_assert(X
{false} == Y
{}); // expected-error {{failed}}
39 static_assert(Y
{} == X
{true});
40 static_assert(Y
{} == X
{false}); // expected-error {{failed}}
42 // x != y -> !(x == y)
43 static_assert(X
{true} != Y
{}); // expected-error {{failed}}
44 static_assert(X
{false} != Y
{});
46 // x != y -> !(y == x)
47 static_assert(Y
{} != X
{true}); // expected-error {{failed}}
48 static_assert(Y
{} != X
{false});