package generator import "testing" func TestPrintDigit (test *testing.T) { testString (test, `%"AAAAAAAAAAAAAAAAAAAAAA==::Byte" = type i8 %"AAAAAAAAAAAAAAAAAAAAAA==::Index" = type i64 define void @"0zNZN147MN2wzMAQ6NS2dQ==::printDigit"(%"AAAAAAAAAAAAAAAAAAAAAA==::Byte" %digit) { 0: %1 = alloca %"AAAAAAAAAAAAAAAAAAAAAA==::Byte" store %"AAAAAAAAAAAAAAAAAAAAAA==::Byte" %digit, ptr %1 %2 = load %"AAAAAAAAAAAAAAAAAAAAAA==::Byte", ptr %1 %3 = alloca %"AAAAAAAAAAAAAAAAAAAAAA==::Byte" store i8 48, ptr %3 %4 = load %"AAAAAAAAAAAAAAAAAAAAAA==::Byte", ptr %3 %5 = add %"AAAAAAAAAAAAAAAAAAAAAA==::Byte" %2, %4 store %"AAAAAAAAAAAAAAAAAAAAAA==::Byte" %5, ptr %1 %6 = call %"AAAAAAAAAAAAAAAAAAAAAA==::Index" @write(i32 1, ptr %1, i64 1) ret void } declare %"AAAAAAAAAAAAAAAAAAAAAA==::Index" @write(i32 %file, ptr %buffer, %"AAAAAAAAAAAAAAAAAAAAAA==::Index" %count) `, ` [write file:I32 buffer:*Byte count:Index]: Index 'write' [printDigit digit:Byte] = { digit = [+ digit '0'] [write 1 [@digit] 1] } `) } func TestSignedUnsignedDivision (test *testing.T) { testString (test, `define void @"0zNZN147MN2wzMAQ6NS2dQ==::main"() { 0: %1 = alloca i64 %2 = sdiv i64 20, -5 store i64 %2, ptr %1 %3 = alloca i64 %4 = sdiv i64 15, 3 store i64 %4, ptr %3 %5 = alloca i64 %6 = srem i64 7, 3 store i64 %6, ptr %5 %7 = alloca i64 %8 = udiv i64 20, 5 store i64 %8, ptr %7 %9 = alloca i64 %10 = udiv i64 15, 3 store i64 %10, ptr %9 %11 = alloca i64 %12 = urem i64 7, 3 store i64 %12, ptr %11 ret void } `, ` [main] = { a:Int = [/ 20 -5] b:Int = [/ 15 3] c:Int = [% 7 3] d:UInt = [/ 20 5] e:UInt = [/ 15 3] f:UInt = [% 7 3] } `) } func TestFloatMath (test *testing.T) { testString (test, `define void @"0zNZN147MN2wzMAQ6NS2dQ==::main"() { 0: %1 = alloca double %2 = fadd double 2.0, 3.0 store double %2, ptr %1 %3 = alloca double %4 = load double, ptr %1 %5 = fmul double %4, 100.0 store double %5, ptr %3 ret void } `, ` [main] = { sum:F64 = [+ 2 3] prd:F64 = [* sum 100] } `) } func TestCompare (test *testing.T) { testString (test, `%"AAAAAAAAAAAAAAAAAAAAAA==::Bool" = type i1 %"0zNZN147MN2wzMAQ6NS2dQ==::A" = type i64 define void @"0zNZN147MN2wzMAQ6NS2dQ==::main"() { 0: %1 = alloca i64 store i64 32, ptr %1 %2 = alloca %"AAAAAAAAAAAAAAAAAAAAAA==::Bool" %3 = load i64, ptr %1 %4 = icmp sgt i64 %3, 1 store i1 %4, ptr %2 %5 = load i64, ptr %1 %6 = icmp slt i64 0, %5 %7 = icmp slt i1 %6, 50 store i1 %7, ptr %2 %8 = load i64, ptr %1 %9 = icmp eq i64 32, %8 store i1 %9, ptr %2 %10 = icmp sgt i64 5, 3 store i1 %10, ptr %2 ret void } `, ` A: Int [main] = { x:Int = 32 b:Bool = [> x 1] b = [< 0 x 50] b = [= 32 x] b = [> [~A 5] [~A 3]] } `) } func TestSlice (test *testing.T) { testString (test, `%"AAAAAAAAAAAAAAAAAAAAAA==::Index" = type i64 %"AAAAAAAAAAAAAAAAAAAAAA==::String" = type { ptr, %"AAAAAAAAAAAAAAAAAAAAAA==::Index" } define void @"0zNZN147MN2wzMAQ6NS2dQ==::print"(%"AAAAAAAAAAAAAAAAAAAAAA==::String" %string) { 0: %1 = alloca %"AAAAAAAAAAAAAAAAAAAAAA==::String" store %"AAAAAAAAAAAAAAAAAAAAAA==::String" %string, ptr %1 %2 = alloca %"AAAAAAAAAAAAAAAAAAAAAA==::String" br label %3 3: %4 = getelementptr { ptr, %"AAAAAAAAAAAAAAAAAAAAAA==::Index" }, ptr %1, i32 0, i32 1 %5 = load %"AAAAAAAAAAAAAAAAAAAAAA==::Index", ptr %4 %6 = icmp ult %"AAAAAAAAAAAAAAAAAAAAAA==::Index" %5, 1 br i1 %6, label %8, label %9 7: ret void 8: br label %7 9: %10 = getelementptr { ptr, %"AAAAAAAAAAAAAAAAAAAAAA==::Index" }, ptr %1, i32 0, i32 0 %11 = load ptr, ptr %10 %12 = call %"AAAAAAAAAAAAAAAAAAAAAA==::Index" @write(i32 1, ptr %11, i64 1) %13 = getelementptr { ptr, %"AAAAAAAAAAAAAAAAAAAAAA==::Index" }, ptr %1, i32 0, i32 0 %14 = load ptr, ptr %13 %15 = getelementptr { ptr, %"AAAAAAAAAAAAAAAAAAAAAA==::Index" }, ptr %1, i32 0, i32 1 %16 = load %"AAAAAAAAAAAAAAAAAAAAAA==::Index", ptr %15 %17 = sub %"AAAAAAAAAAAAAAAAAAAAAA==::Index" %16, 1 %18 = getelementptr i8, ptr %14, i64 1 %19 = getelementptr %"AAAAAAAAAAAAAAAAAAAAAA==::String", ptr %2, i32 0, i32 0 store ptr %18, ptr %19 %20 = getelementptr %"AAAAAAAAAAAAAAAAAAAAAA==::String", ptr %2, i32 0, i32 1 store %"AAAAAAAAAAAAAAAAAAAAAA==::Index" %17, ptr %20 %21 = load %"AAAAAAAAAAAAAAAAAAAAAA==::String", ptr %2 store %"AAAAAAAAAAAAAAAAAAAAAA==::String" %21, ptr %1 br label %3 } declare %"AAAAAAAAAAAAAAAAAAAAAA==::Index" @write(i32 %file, ptr %buffer, %"AAAAAAAAAAAAAAAAAAAAAA==::Index" %count) `, ` [write file:I32 buffer:*Byte count:Index]: Index 'write' [print string: String] = loop { if [< [#string] 1] then [break] [write 1 [~*Byte string] 1] string = [\string 1/] } `) }