1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146
|
// Test ldc.attributes.callingConvention
// To make testing easier (no exhaustive test for all recognized calling convention names), we choose to test only X86.
// REQUIRES: target_X86
// RUN: %ldc -mtriple=x86_64-linux-gnu -c -output-ll -of=%t.ll %s && FileCheck %s < %t.ll
import ldc.attributes;
//////////////////////////////////////////////////////////
/// Normal (D) function calls and invokes:
// CHECK-LABEL: define x86_vectorcallcc void @{{.*}}foofoofoo
@callingConvention("vectorcall") void foofoofoo()
{
}
// CHECK-LABEL: define{{.*}} @{{.*}}foocallsfoofoofoo
void foocallsfoofoofoo()
{
// CHECK: call x86_vectorcallcc void @{{.*}}attr_callingconvention9foofoofoo
foofoofoo();
}
// CHECK-LABEL: define{{.*}} @{{.*}}fooinvokesfoofoofoo
void fooinvokesfoofoofoo()
{
RAII force_invoke;
// CHECK: invoke x86_vectorcallcc void @{{.*}}attr_callingconvention9foofoofoo
foofoofoo();
}
//////////////////////////////////////////////////////////
/// Extern (D) function calls and invokes:
// CHECK-LABEL: define x86_vectorcallcc void @fooexternCfoofoo
extern(C) @callingConvention("vectorcall") void fooexternCfoofoo()
{
}
// CHECK-LABEL: define{{.*}} @{{.*}}foocallsexternCfoofoofoo
void foocallsexternCfoofoofoo()
{
// CHECK: call x86_vectorcallcc void @{{.*}}fooexternCfoofoo
fooexternCfoofoo();
}
// CHECK-LABEL: define{{.*}} @{{.*}}fooinvokesexternCfoofoofoo
void fooinvokesexternCfoofoofoo()
{
RAII force_invoke;
// CHECK: invoke x86_vectorcallcc void @{{.*}}fooexternCfoofoo
fooexternCfoofoo();
}
//////////////////////////////////////////////////////////
/// Forward-declared function calls and invokes:
// CHECK-LABEL: define{{.*}} @{{.*}}attr_callingconvention34foocalls_forward_declared_function
void foocalls_forward_declared_function()
{
// CHECK: call x86_vectorcallcc void @{{.*}}attr_callingconvention25forward_declared_function
forward_declared_function();
}
// CHECK-LABEL: declare x86_vectorcallcc void @{{.*}}forward_declared_function
@callingConvention("vectorcall") void forward_declared_function();
// CHECK-LABEL: define{{.*}} @{{.*}}attr_callingconvention36fooinvokes_forward_declared_function
void fooinvokes_forward_declared_function()
{
RAII force_invoke;
// CHECK: invoke x86_vectorcallcc void @{{.*}}attr_callingconvention25forward_declared_function
forward_declared_function();
}
//////////////////////////////////////////////////////////
/// Struct function calls and invokes:
struct A {
@callingConvention("vectorcall") void struct_method() {}
}
// CHECK-LABEL: define{{.*}} @{{.*}}foocalls_struct_method
void foocalls_struct_method()
{
A a;
// CHECK: call x86_vectorcallcc void @{{.*}}struct_method
a.struct_method();
}
// CHECK-LABEL: define{{.*}} @{{.*}}fooinvokes_struct_method
void fooinvokes_struct_method()
{
RAII force_invoke;
A a;
// CHECK: invoke x86_vectorcallcc void @{{.*}}struct_method
a.struct_method();
}
//////////////////////////////////////////////////////////
/// Class virtual function calls and invokes:
class C {
@callingConvention("default") @callingConvention("vectorcall") void virtual_method() {}
}
// CHECK-LABEL: define{{.*}} @{{.*}}foocalls_virtual_method
void foocalls_virtual_method()
{
C c = new C;
// CHECK: call x86_vectorcallcc void %virtual_method
c.virtual_method();
}
// CHECK-LABEL: define{{.*}} @{{.*}}fooinvokes_virtual_method
void fooinvokes_virtual_method()
{
RAII force_invoke;
C c;
// CHECK: invoke x86_vectorcallcc void %virtual_method
c.virtual_method();
}
//////////////////////////////////////////////////////////
// Check scope rule, multiple application
@callingConvention("vectorcall"):
// CHECK-LABEL: define void @{{.*}}gggscopeggg
@callingConvention("default") void gggscopeggg()
{
}
// CHECK-LABEL: define x86_vectorcallcc void @{{.*}}fooscopefoofoo
void fooscopefoofoo()
{
}
@callingConvention("default"):
//////////////////////////////////////////////////////////
// RAII struct to force `invoke` on function calls.
struct RAII {
~this() {}
}
|