1ba15d186SMark de Wever // RUN: %clang_cc1 -std=c++23 %s -emit-llvm -triple x86_64-linux -o - | FileCheck %s
2ba15d186SMark de Wever // RUN: %clang_cc1 -std=c++23 %s -emit-llvm -triple x86_64-windows-msvc -o - | FileCheck %s
33faf1f17SRoy Jacobson
43faf1f17SRoy Jacobson struct Functor {
operator []Functor53faf1f17SRoy Jacobson static int operator[](int x, int y) {
63faf1f17SRoy Jacobson return x + y;
73faf1f17SRoy Jacobson }
83faf1f17SRoy Jacobson };
93faf1f17SRoy Jacobson
GetAFunctor()10*ee01a2c3STianlan Zhou Functor GetAFunctor() {
11*ee01a2c3STianlan Zhou return {};
12*ee01a2c3STianlan Zhou }
13*ee01a2c3STianlan Zhou
call_static_subscript_operator()143faf1f17SRoy Jacobson void call_static_subscript_operator() {
153faf1f17SRoy Jacobson Functor f;
163faf1f17SRoy Jacobson f[101, 102];
173faf1f17SRoy Jacobson f.operator[](201, 202);
183faf1f17SRoy Jacobson Functor{}[301, 302];
193faf1f17SRoy Jacobson Functor::operator[](401, 402);
20*ee01a2c3STianlan Zhou GetAFunctor()[501, 502];
213faf1f17SRoy Jacobson }
223faf1f17SRoy Jacobson
233faf1f17SRoy Jacobson // CHECK: define {{.*}}call_static_subscript_operator{{.*}}
243faf1f17SRoy Jacobson // CHECK-NEXT: entry:
253faf1f17SRoy Jacobson // CHECK: {{.*}} = call noundef i32 {{.*}}Functor{{.*}}(i32 noundef 101, i32 noundef 102)
263faf1f17SRoy Jacobson // CHECK-NEXT: {{.*}} = call noundef i32 {{.*}}Functor{{.*}}(i32 noundef 201, i32 noundef 202)
273faf1f17SRoy Jacobson // CHECK-NEXT: {{.*}} = call noundef i32 {{.*}}Functor{{.*}}(i32 noundef 301, i32 noundef 302)
283faf1f17SRoy Jacobson // CHECK-NEXT: {{.*}} = call noundef i32 {{.*}}Functor{{.*}}(i32 noundef 401, i32 noundef 402)
29*ee01a2c3STianlan Zhou // CHECK: {{.*}}call {{.*}}GetAFunctor{{.*}}()
30*ee01a2c3STianlan Zhou // CHECK-NEXT: {{.*}} = call noundef i32 {{.*}}Functor{{.*}}(i32 noundef 501, i32 noundef 502)
313faf1f17SRoy Jacobson // CHECK-NEXT: ret void
323faf1f17SRoy Jacobson // CHECK-NEXT: }
333faf1f17SRoy Jacobson
343faf1f17SRoy Jacobson struct FunctorConsteval {
operator []FunctorConsteval353faf1f17SRoy Jacobson consteval static int operator[](int x, int y) {
363faf1f17SRoy Jacobson return x + y;
373faf1f17SRoy Jacobson }
383faf1f17SRoy Jacobson };
393faf1f17SRoy Jacobson
403faf1f17SRoy Jacobson struct FunctorConstexpr {
operator []FunctorConstexpr413faf1f17SRoy Jacobson constexpr static int operator[](int x, int y) {
423faf1f17SRoy Jacobson return x + y;
433faf1f17SRoy Jacobson }
443faf1f17SRoy Jacobson };
453faf1f17SRoy Jacobson
test_consteval_constexpr()463faf1f17SRoy Jacobson void test_consteval_constexpr() {
473faf1f17SRoy Jacobson int x = 0;
483faf1f17SRoy Jacobson int y = FunctorConstexpr{}[x, 2];
493faf1f17SRoy Jacobson constexpr int z1 = FunctorConsteval{}[2, 2];
503faf1f17SRoy Jacobson constexpr int z2 = FunctorConstexpr{}[2, 2];
513faf1f17SRoy Jacobson
523faf1f17SRoy Jacobson static_assert(z1 == 4);
533faf1f17SRoy Jacobson static_assert(z2 == 4);
543faf1f17SRoy Jacobson }
553faf1f17SRoy Jacobson
563faf1f17SRoy Jacobson template <class T>
573faf1f17SRoy Jacobson struct DepFunctor {
operator []DepFunctor583faf1f17SRoy Jacobson static int operator[](T t) {
593faf1f17SRoy Jacobson return int(t);
603faf1f17SRoy Jacobson }
613faf1f17SRoy Jacobson };
623faf1f17SRoy Jacobson
test_dep_functors()633faf1f17SRoy Jacobson void test_dep_functors() {
643faf1f17SRoy Jacobson int x = DepFunctor<float>{}[1.0f];
653faf1f17SRoy Jacobson int y = DepFunctor<bool>{}[true];
663faf1f17SRoy Jacobson }
673faf1f17SRoy Jacobson
683faf1f17SRoy Jacobson // CHECK: define {{.*}}test_dep_functors{{.*}}
693faf1f17SRoy Jacobson // CHECK-NEXT: entry:
70*ee01a2c3STianlan Zhou // CHECK: {{.*}} = call noundef i32 {{.*}}DepFunctor{{.*}}(float noundef 1.000000e+00)
71*ee01a2c3STianlan Zhou // CHECK: {{.*}} = call noundef i32 {{.*}}DepFunctor{{.*}}(i1 noundef zeroext true)
723faf1f17SRoy Jacobson // CHECK: ret void
733faf1f17SRoy Jacobson // CHECK-NEXT: }
74