mirror of
https://github.com/c3lang/c3c.git
synced 2026-02-27 12:01:16 +00:00
345 lines
8.0 KiB
C
345 lines
8.0 KiB
C
// #target: macos-x64
|
|
module test;
|
|
|
|
struct Foo { int x, y; }
|
|
Foo[10] array;
|
|
|
|
fn void foo() {}
|
|
|
|
fn void *dlclose(void*);
|
|
|
|
fn void ap_os_dso_unload(void *handle)
|
|
{
|
|
dlclose(handle);
|
|
return;
|
|
}
|
|
|
|
extern fn void foo2(int, double, float);
|
|
|
|
fn void bar(int x) {
|
|
foo2(x, x ? 1.0 : 12.5, 1.0f);
|
|
}
|
|
|
|
extern fn int tolower(int);
|
|
|
|
fn char *rangematch(char *pattern, int teste, int c) {
|
|
|
|
if ((c <= teste) | (tolower(c) <= tolower((char)(teste)))) return (char*)(0);
|
|
|
|
return pattern;
|
|
}
|
|
|
|
struct Foostruct {
|
|
short x;
|
|
}
|
|
|
|
extern fn int foo3(Foostruct ic);
|
|
|
|
fn void teste2() {
|
|
Foostruct xqic;
|
|
foo3(xqic);
|
|
}
|
|
|
|
struct Vertex
|
|
{
|
|
float a, b, c;
|
|
}
|
|
struct Edge_rec
|
|
{
|
|
Vertex *v;
|
|
Edge_rec *next;
|
|
int wasseen;
|
|
int more_data;
|
|
}
|
|
|
|
define QuadEdge = Edge_rec*;
|
|
|
|
struct EdgePair {
|
|
QuadEdge left, right;
|
|
}
|
|
|
|
struct EdgeStack {
|
|
int ptr;
|
|
QuadEdge *elts;
|
|
int stack_size;
|
|
}
|
|
|
|
fn int do_merge(QuadEdge ldo, QuadEdge rdo) {
|
|
int lvalid;
|
|
QuadEdge basel;
|
|
QuadEdge rcand;
|
|
while (1) {
|
|
if (!lvalid) {
|
|
return (int)((iptr)(basel.next));
|
|
}
|
|
}
|
|
return 1;
|
|
}
|
|
|
|
fn int test(int x) {
|
|
return x;
|
|
}
|
|
|
|
fn void abc(int *x);
|
|
fn int def(int y, int z) {
|
|
abc(&z);
|
|
return y;
|
|
}
|
|
|
|
struct Test { short x, x2; int y, z; }
|
|
|
|
fn int testing(Test *a) {
|
|
return a.x2+a.y;
|
|
}
|
|
|
|
fn int test2(int x, Test a, int y) {
|
|
return x+y+a.x2+a.y;
|
|
}
|
|
fn int test3(Test a, Test b) {
|
|
return a.x2+a.y+b.y+b.z;
|
|
}
|
|
|
|
fn Test test4(Test a) {
|
|
return a;
|
|
}
|
|
|
|
fn int test6() {
|
|
int[200] b;
|
|
return b[4];
|
|
}
|
|
|
|
struct STest2 { int x; short[4] y; double z; }
|
|
|
|
fn STest2 test7(STest2 x) {
|
|
return x;
|
|
}
|
|
|
|
extern fn int printf(char * format, ...);
|
|
|
|
fn int main2() {
|
|
long v = 123455678902i64;
|
|
printf("%lld\n", v);
|
|
return 1;
|
|
}
|
|
|
|
double afoo = 17;
|
|
double abar = 12.0;
|
|
float axx = 12.0f;
|
|
|
|
char*[*] procnames = {
|
|
"EXIT"
|
|
};
|
|
|
|
void *[*] data = { &afoo, &abar, &axx };
|
|
|
|
/* #expect: test.ll
|
|
|
|
%Foo = type { i32, i32 }
|
|
%Foostruct = type { i16 }
|
|
%Edge_rec = type { ptr, ptr, i32, i32 }
|
|
%Test = type { i16, i16, i32, i32 }
|
|
%STest2 = type { i32, [4 x i16], double }
|
|
|
|
@test_array = local_unnamed_addr global [10 x %Foo] zeroinitializer, align 16
|
|
@test_afoo = global double 1.700000e+01, align 8
|
|
@test_abar = global double 1.200000e+01, align 8
|
|
@test_axx = global float 1.200000e+01, align 4
|
|
@.str = private unnamed_addr constant [5 x i8] c"EXIT\00", align 1
|
|
@test_procnames = local_unnamed_addr global [1 x ptr] [ptr @.str], align 8
|
|
@test_data = local_unnamed_addr global [3 x ptr] [ptr @test_afoo, ptr @test_abar, ptr @test_axx], align 16
|
|
@.str.6 = private unnamed_addr constant [6 x i8] c"%lld\0A\00", align 1
|
|
|
|
define void @test_foo() #0 {
|
|
entry:
|
|
ret void
|
|
}
|
|
|
|
declare ptr @test_dlclose(ptr) #0
|
|
|
|
define void @test_ap_os_dso_unload(ptr %0) #0 {
|
|
entry:
|
|
%1 = call ptr @test_dlclose(ptr %0)
|
|
ret void
|
|
}
|
|
|
|
declare void @foo2(i32, double, float) #0
|
|
|
|
define void @test_bar(i32 %0) #0 {
|
|
entry:
|
|
%intbool = icmp ne i32 %0, 0
|
|
%ternary = select i1 %intbool, double 1.000000e+00, double 1.250000e+01
|
|
call void @foo2(i32 %0, double %ternary, float 1.000000e+00)
|
|
ret void
|
|
}
|
|
|
|
declare i32 @tolower(i32) #0
|
|
|
|
define ptr @test_rangematch(ptr %0, i32 %1, i32 %2) #0 {
|
|
entry:
|
|
%le = icmp sle i32 %2, %1
|
|
%3 = call i32 @tolower(i32 %2)
|
|
%siuitrunc = trunc i32 %1 to i8
|
|
%uisiext = zext i8 %siuitrunc to i32
|
|
%4 = call i32 @tolower(i32 %uisiext)
|
|
%le1 = icmp sle i32 %3, %4
|
|
%or = or i1 %le, %le1
|
|
br i1 %or, label %if.then, label %if.exit
|
|
|
|
if.then: ; preds = %entry
|
|
ret ptr null
|
|
|
|
if.exit: ; preds = %entry
|
|
ret ptr %0
|
|
}
|
|
|
|
declare i32 @foo3(i16) #0
|
|
|
|
define void @test_teste2() #0 {
|
|
entry:
|
|
%xqic = alloca %Foostruct, align 2
|
|
store i16 0, ptr %xqic, align 2
|
|
%0 = getelementptr inbounds %Foostruct, ptr %xqic, i32 0, i32 0
|
|
%1 = load i16, ptr %0, align 2
|
|
%2 = call i32 @foo3(i16 %1)
|
|
ret void
|
|
}
|
|
|
|
define i32 @test_do_merge(ptr %0, ptr %1) #0 {
|
|
entry:
|
|
%lvalid = alloca i32, align 4
|
|
%basel = alloca ptr, align 8
|
|
%rcand = alloca ptr, align 8
|
|
store i32 0, ptr %lvalid, align 4
|
|
store ptr null, ptr %basel, align 8
|
|
store ptr null, ptr %rcand, align 8
|
|
br label %loop.body
|
|
|
|
loop.body: ; preds = %if.exit, %entry
|
|
%2 = load i32, ptr %lvalid, align 4
|
|
%not = icmp eq i32 %2, 0
|
|
br i1 %not, label %if.then, label %if.exit
|
|
|
|
if.then: ; preds = %loop.body
|
|
%3 = load ptr, ptr %basel, align 8
|
|
%4 = getelementptr inbounds %Edge_rec, ptr %3, i32 0, i32 1
|
|
%5 = load ptr, ptr %4, align 8
|
|
%ptrxi = ptrtoint ptr %5 to i32
|
|
ret i32 %ptrxi
|
|
|
|
if.exit: ; preds = %loop.body
|
|
br label %loop.body
|
|
|
|
loop.exit: ; No predecessors!
|
|
ret i32 1
|
|
}
|
|
|
|
define i32 @test_test(i32 %0) #0 {
|
|
entry:
|
|
ret i32 %0
|
|
}
|
|
|
|
declare void @test_abc(ptr) #0
|
|
|
|
define i32 @test_def(i32 %0, i32 %1) #0 {
|
|
entry:
|
|
%z = alloca i32, align 4
|
|
store i32 %1, ptr %z, align 4
|
|
call void @test_abc(ptr %z)
|
|
ret i32 %0
|
|
}
|
|
|
|
define i32 @test_testing(ptr %0) #0 {
|
|
entry:
|
|
%1 = getelementptr inbounds %Test, ptr %0, i32 0, i32 1
|
|
%2 = load i16, ptr %1, align 2
|
|
%sisiext = sext i16 %2 to i32
|
|
%3 = getelementptr inbounds %Test, ptr %0, i32 0, i32 2
|
|
%4 = load i32, ptr %3, align 4
|
|
%add = add i32 %sisiext, %4
|
|
ret i32 %add
|
|
}
|
|
|
|
define i32 @test_test2(i32 %0, i64 %1, i32 %2, i32 %3) #0 {
|
|
entry:
|
|
%4 = alloca { i64, i32 }, align 8
|
|
%5 = getelementptr inbounds { i64, i32 }, ptr %4, i32 0, i32 0
|
|
store i64 %1, ptr %5, align 8
|
|
%6 = getelementptr inbounds { i64, i32 }, ptr %4, i32 0, i32 1
|
|
store i32 %2, ptr %6, align 8
|
|
%add = add i32 %0, %3
|
|
%7 = getelementptr inbounds %Test, ptr %4, i32 0, i32 1
|
|
%8 = load i16, ptr %7, align 2
|
|
%sisiext = sext i16 %8 to i32
|
|
%add1 = add i32 %add, %sisiext
|
|
%9 = getelementptr inbounds %Test, ptr %4, i32 0, i32 2
|
|
%10 = load i32, ptr %9, align 4
|
|
%add2 = add i32 %add1, %10
|
|
ret i32 %add2
|
|
}
|
|
|
|
define i32 @test_test3(i64 %0, i32 %1, i64 %2, i32 %3) #0 {
|
|
entry:
|
|
%4 = alloca { i64, i32 }, align 8
|
|
%5 = alloca { i64, i32 }, align 8
|
|
%6 = getelementptr inbounds { i64, i32 }, ptr %4, i32 0, i32 0
|
|
store i64 %0, ptr %6, align 8
|
|
%7 = getelementptr inbounds { i64, i32 }, ptr %4, i32 0, i32 1
|
|
store i32 %1, ptr %7, align 8
|
|
%8 = getelementptr inbounds { i64, i32 }, ptr %5, i32 0, i32 0
|
|
store i64 %2, ptr %8, align 8
|
|
%9 = getelementptr inbounds { i64, i32 }, ptr %5, i32 0, i32 1
|
|
store i32 %3, ptr %9, align 8
|
|
%10 = getelementptr inbounds %Test, ptr %4, i32 0, i32 1
|
|
%11 = load i16, ptr %10, align 2
|
|
%sisiext = sext i16 %11 to i32
|
|
%12 = getelementptr inbounds %Test, ptr %4, i32 0, i32 2
|
|
%13 = load i32, ptr %12, align 4
|
|
%add = add i32 %sisiext, %13
|
|
%14 = getelementptr inbounds %Test, ptr %5, i32 0, i32 2
|
|
%15 = load i32, ptr %14, align 4
|
|
%add1 = add i32 %add, %15
|
|
%16 = getelementptr inbounds %Test, ptr %5, i32 0, i32 3
|
|
%17 = load i32, ptr %16, align 8
|
|
%add2 = add i32 %add1, %17
|
|
ret i32 %add2
|
|
}
|
|
|
|
define { i64, i32 } @test_test4(i64 %0, i32 %1) #0 {
|
|
entry:
|
|
%2 = alloca { i64, i32 }, align 8
|
|
%tempcoerce = alloca { i64, i32 }, align 8
|
|
%3 = getelementptr inbounds { i64, i32 }, ptr %2, i32 0, i32 0
|
|
store i64 %0, ptr %3, align 8
|
|
%4 = getelementptr inbounds { i64, i32 }, ptr %2, i32 0, i32 1
|
|
store i32 %1, ptr %4, align 8
|
|
call void @llvm.memcpy.p0.p0.i32(ptr align 8 %tempcoerce, ptr align 8 %2, i32 12, i1 false)
|
|
%5 = load { i64, i32 }, ptr %tempcoerce, align 8
|
|
ret { i64, i32 } %5
|
|
}
|
|
|
|
define i32 @test_test6() #0 {
|
|
entry:
|
|
%b = alloca [200 x i32], align 16
|
|
call void @llvm.memset.p0.i64(ptr align 16 %b, i8 0, i64 800, i1 false)
|
|
%0 = getelementptr inbounds [200 x i32], ptr %b, i64 0, i64 4
|
|
%1 = load i32, ptr %0, align 4
|
|
ret i32 %1
|
|
}
|
|
|
|
define void @test_test7(ptr noalias sret(%STest2) align 8 %0, ptr byval(%STest2) align 8 %1) #0 {
|
|
entry:
|
|
call void @llvm.memcpy.p0.p0.i32(ptr align 8 %0, ptr align 8 %1, i32 24, i1 false)
|
|
ret void
|
|
}
|
|
|
|
declare i32 @printf(ptr, ...) #0
|
|
|
|
define i32 @test_main2() #0 {
|
|
entry:
|
|
%v = alloca i64, align 8
|
|
store i64 123455678902, ptr %v, align 8
|
|
%0 = load i64, ptr %v, align 8
|
|
%1 = call i32 (ptr, ...) @printf(ptr @.str.6, i64 %0)
|
|
ret i32 1
|
|
}
|