blob: e3fe05dfa34fa6ae1c846ccc9f533d772a0b2bc2 [file] [edit]
// RUN: %clang_cc1 -triple x86_64-unknown-linux-gnu -std=c++17 -fclangir -emit-cir -mmlir -mlir-print-ir-before=cir-cxxabi-lowering %s -o %t.cir 2> %t-before.cir
// RUN: FileCheck --check-prefix=CIR-BEFORE --input-file=%t-before.cir %s
// RUN: FileCheck --check-prefix=CIR-AFTER --input-file=%t.cir %s
// RUN: %clang_cc1 -triple x86_64-unknown-linux-gnu -std=c++17 -fclangir -emit-llvm %s -o %t-cir.ll
// RUN: FileCheck --input-file=%t-cir.ll --check-prefix=LLVM %s
// RUN: %clang_cc1 -triple x86_64-unknown-linux-gnu -std=c++17 -emit-llvm %s -o %t.ll
// RUN: FileCheck --check-prefix=OGCG --input-file=%t.ll %s
struct Foo {
void m1(int);
virtual void m2(int);
virtual void m3(int);
};
void unused_pointer_to_member_func(void (Foo::*func)(int)) {
}
// CIR-BEFORE: cir.func {{.*}} @_Z29unused_pointer_to_member_funcM3FooFviE(%[[ARG:.*]]: !cir.method<!cir.func<(!s32i)> in !rec_Foo>)
// CIR-BEFORE: %[[FUNC:.*]] = cir.alloca !cir.method<!cir.func<(!s32i)> in !rec_Foo>, !cir.ptr<!cir.method<!cir.func<(!s32i)> in !rec_Foo>>, ["func", init]
// CIR-AFTER: !rec_anon_struct = !cir.record<struct {!s64i, !s64i}>
// CIR-AFTER: cir.func {{.*}} @_Z29unused_pointer_to_member_funcM3FooFviE(%[[ARG:.*]]: !rec_anon_struct {{.*}})
// CIR-AFTER %[[FUNC:.*]] = cir.alloca !rec_anon_struct, !cir.ptr<!rec_anon_struct>, ["func", init]
// NOTE: The difference between LLVM and OGCG are due to the lack of calling convention handling in CIR.
// LLVM: define {{.*}} void @_Z29unused_pointer_to_member_funcM3FooFviE({ i64, i64 } %[[ARG:.*]])
// LLVM: %[[FUNC:.*]] = alloca { i64, i64 }
// LLVM: store { i64, i64 } %[[ARG]], ptr %[[FUNC]]
// OGCG: define {{.*}} void @_Z29unused_pointer_to_member_funcM3FooFviE(i64 %[[FUNC_COERCE0:.*]], i64 %[[FUNC_COERCE1:.*]])
// OGCG: %[[FUNC:.*]] = alloca { i64, i64 }
// OGCG: %[[FUNC_ADDR:.*]] = alloca { i64, i64 }
// OGCG: %[[FUNC_0:.*]] = getelementptr inbounds nuw { i64, i64 }, ptr %[[FUNC]], i32 0, i32 0
// OGCG: store i64 %[[FUNC_COERCE0]], ptr %[[FUNC_0]]
// OGCG: %[[FUNC_1:.*]] = getelementptr inbounds nuw { i64, i64 }, ptr %[[FUNC]], i32 0, i32 1
// OGCG: store i64 %[[FUNC_COERCE1]], ptr %[[FUNC_1]]
// OGCG: %[[FUNC1:.*]] = load { i64, i64 }, ptr %[[FUNC]]
// OGCG: store { i64, i64 } %[[FUNC1]], ptr %[[FUNC_ADDR]]