aboutsummaryrefslogtreecommitdiff
path: root/rts.ll
diff options
context:
space:
mode:
Diffstat (limited to 'rts.ll')
-rw-r--r--rts.ll103
1 files changed, 71 insertions, 32 deletions
diff --git a/rts.ll b/rts.ll
index c0f4a86..180a683 100644
--- a/rts.ll
+++ b/rts.ll
@@ -6,9 +6,12 @@ declare i64 @printf(i8*, ...)
@printf_d = private unnamed_addr constant [3 x i8] c"%d\00", align 1
@printf_c = private unnamed_addr constant [3 x i8] c"%c\00", align 1
@printf_cycle = private unnamed_addr constant [16 x i8] c"cycle in spine\0a\00", align 1
+@printf_gc = private unnamed_addr constant [11 x i8] c"heap full\0a\00", align 1
attributes #0 = { alwaysinline }
+%Hp = type {i64*,i64}
+
define private i64* @_alloc_heap(i64 %n) alwaysinline {
%s.0 = alloca i64
%s.1 = getelementptr i64, i64* %s.0, i64 1
@@ -73,6 +76,22 @@ loop.0:
br label %loop
}
+define private %Hp @_need_free_words(i64 %n, %Hp %hp_s.0) #0 {
+ %hp_free.0 = extractvalue %Hp %hp_s.0, 1
+ %hp_free.1 = sub i64 %hp_free.0, %n
+
+ %lt = icmp slt i64 %hp_free.1, 0
+ br i1 %lt, label %gc, label %ok
+ok:
+ %hp_s.1 = insertvalue %Hp %hp_s.0, i64 %hp_free.1, 1
+ ret %Hp %hp_s.1
+
+gc:
+ ; TODO
+ call i64 (i8*, ...) @printf(i8* getelementptr inbounds ([11 x i8], [11 x i8]* @printf_gc, i64 0, i64 0))
+ unreachable
+}
+
define private i64* @addI(i64* %bsp.0) #0 {
%t.0 = load i64, i64* %bsp.0
store i64 undef, i64* %bsp.0
@@ -83,27 +102,41 @@ define private i64* @addI(i64* %bsp.0) #0 {
ret i64* %bsp.1
}
-; TODO gc
-; TODO for arity < 2, we must reserve more space on the heap
-define private {i64**,i64*} @build(i64* %label, i64 %arity, i64** %asp.0, i64** %aspstart, i64** %globasp.0, i64* %hp.0) #0 {
+define private {i64**,%Hp} @build(i64* %label, i64 %arity, i64** %asp.0, i64** %aspstart, i64** %globasp.0, %Hp %hp_s.0) #0 {
entry:
+ %arity_p1 = add i64 %arity, 1
+ %lt = icmp slt i64 %arity, 2
+ br i1 %lt, label %arity_lt2, label %arity_ge2
+
+arity_lt2:
+ br label %arity_ge2
+
+arity_ge2:
+ %n_words = phi i64 [%arity_p1, %entry], [3, %arity_lt2]
+ %hp_s.1 = call %Hp @_need_free_words(i64 %arity_p1, %Hp %hp_s.0)
+ %hp.0 = extractvalue %Hp %hp_s.1, 0
+ %hp_free.0 = extractvalue %Hp %hp_s.1, 1
+
%label.0 = ptrtoint i64* %label to i64
store i64 %label.0, i64* %hp.0
%hp.1 = getelementptr i64, i64* %hp.0, i64 1
br label %loop
loop:
- %asp.1 = phi i64** [%asp.0, %entry], [%asp.2, %loop.0]
- %hp.2 = phi i64* [%hp.1, %entry], [%hp.3, %loop.0]
- %arity.0 = phi i64 [%arity, %entry], [%arity.1, %loop.0]
+ %asp.1 = phi i64** [%asp.0, %arity_ge2], [%asp.2, %loop.0]
+ %hp.2 = phi i64* [%hp.1, %arity_ge2], [%hp.3, %loop.0]
+ %arity.0 = phi i64 [%arity, %arity_ge2], [%arity.1, %loop.0]
%t.0 = icmp eq i64 %arity.0, 0
br i1 %t.0, label %done, label %loop.0
done:
%asp.3 = getelementptr i64*, i64** %asp.1, i64 1
store i64* %hp.0, i64** %asp.3
- %ret.0 = insertvalue {i64**,i64*} undef, i64** %asp.3, 0
- %ret.1 = insertvalue {i64**,i64*} %ret.0, i64* %hp.2, 1
- ret {i64**,i64*} %ret.1
+ %ret.0 = insertvalue {i64**,%Hp} undef, i64** %asp.3, 0
+ %hp.4 = getelementptr i64, i64* %hp.0, i64 %n_words
+ %hp_s.2 = insertvalue %Hp %hp_s.1, i64* %hp.4, 0
+ %hp_s.3 = insertvalue %Hp %hp_s.2, i64 %hp_free.0, 1 ; TODO
+ %ret.1 = insertvalue {i64**,%Hp} %ret.0, %Hp %hp_s.3, 1
+ ret {i64**,%Hp} %ret.1
loop.0:
%t.1 = call i64* @peek_a(i64** %asp.1)
@@ -115,11 +148,15 @@ loop.0:
br label %loop
}
-; TODO pass aspstart for gc
-define private {i64**,i64*} @buildI(i64 %i, i64** %asp.0, i64* %hp.0) #0 {
- %INT.0 = ptrtoint {i64, i64, i64*, i64, i8, i8, i8}* @INT to i64
- %INT.1 = add i64 %INT.0, 2
- store i64 %INT.1, i64* %hp.0
+define private {i64**,%Hp} @buildI(i64 %i, i64** %asp.0, %Hp %hp_s.0) #0 {
+ %hp_s.1 = call %Hp @_need_free_words(i64 2, %Hp %hp_s.0)
+ %hp.0 = extractvalue %Hp %hp_s.1, 0
+ %hp_free.0 = extractvalue %Hp %hp_s.1, 1
+
+ %INT.0 = bitcast {i64, i64, i64*, i64, i8, i8, i8}* @INT to i8*
+ %INT.1 = getelementptr i8, i8* %INT.0, i64 2
+ %INT.2 = ptrtoint i8* %INT.1 to i64
+ store i64 %INT.2, i64* %hp.0
%hp.1 = getelementptr i64, i64* %hp.0, i64 1
store i64 %i, i64* %hp.1
@@ -128,9 +165,10 @@ define private {i64**,i64*} @buildI(i64 %i, i64** %asp.0, i64* %hp.0) #0 {
store i64* %hp.0, i64** %asp.1
%hp.2 = getelementptr i64, i64* %hp.0, i64 2
- %ret.0 = insertvalue {i64**,i64*} undef, i64** %asp.1, 0
- %ret.1 = insertvalue {i64**,i64*} %ret.0, i64* %hp.2, 1
- ret {i64**,i64*} %ret.1
+ %ret.0 = insertvalue {i64**,%Hp} undef, i64** %asp.1, 0
+ %hp_s.2 = insertvalue %Hp %hp_s.1, i64* %hp.2, 0
+ %ret.1 = insertvalue {i64**,%Hp} %ret.0, %Hp %hp_s.2, 1
+ ret {i64**,%Hp} %ret.1
}
define private i64* @eqI_b(i64 %i, i64 %n, i64* %bsp.0) #0 {
@@ -150,9 +188,10 @@ define private i64** @fillI_b(i64 %b_offset, i64 %a_offset, i64* %bsp.0, i64** %
%asp.1 = getelementptr i64*, i64** %asp.0, i64 %a_offset
%n.0 = load i64*, i64** %asp.1
- %INT.0 = ptrtoint {i64, i64, i64*, i64, i8, i8, i8}* @INT to i64
- %INT.1 = add i64 %INT.0, 2
- store i64 %INT.1, i64* %n.0
+ %INT.0 = bitcast {i64, i64, i64*, i64, i8, i8, i8}* @INT to i8*
+ %INT.1 = getelementptr i8, i8* %INT.0, i64 2
+ %INT.2 = ptrtoint i8* %INT.1 to i64
+ store i64 %INT.2, i64* %n.0
%n.1 = getelementptr i64, i64* %n.0, i64 1
store i64 %t.0, i64* %n.1
@@ -160,7 +199,7 @@ define private i64** @fillI_b(i64 %b_offset, i64 %a_offset, i64* %bsp.0, i64** %
ret i64** %asp.0
}
-define private {i64*,i64**} @jsr_eval(i64 %n, i64** %asp.0, i64** %aspstart, i64** %globasp.0, i64* %hp.0) #0 {
+define private {%Hp,i64**} @jsr_eval(i64 %n, i64** %asp.0, i64** %aspstart, i64** %globasp.0, %Hp %hp.0) #0 {
%asp.1 = getelementptr i64*, i64** %asp.0, i64 %n
%n.0 = load i64*, i64** %asp.1
@@ -171,23 +210,23 @@ define private {i64*,i64**} @jsr_eval(i64 %n, i64** %asp.0, i64** %aspstart, i64
br i1 %t.1, label %eval, label %done
done:
- %r.0 = insertvalue {i64*,i64**} undef, i64* %hp.0, 0
- %r.1 = insertvalue {i64*,i64**} %r.0, i64** %globasp.0, 1
- ret {i64*,i64**} %r.1
+ %r.0 = insertvalue {%Hp,i64**} undef, %Hp %hp.0, 0
+ %r.1 = insertvalue {%Hp,i64**} %r.0, i64** %globasp.0, 1
+ ret {%Hp,i64**} %r.1
eval:
%globasp.1 = call i64** @_push_local_astack(i64** %asp.0, i64** %aspstart, i64** %globasp.0)
- %nentry.0 = inttoptr i64 %d.0 to {i64*,i64**,i64*} (i64*, i64**, i64*)*
- %t.2 = call {i64*,i64**,i64*} %nentry.0(i64* %hp.0, i64** %globasp.1, i64* %n.0)
- %hp.1 = extractvalue {i64*,i64**,i64*} %t.2, 0
- %globasp.2 = extractvalue {i64*,i64**,i64*} %t.2, 1
- %n.1 = extractvalue {i64*,i64**,i64*} %t.2, 2
+ %nentry.0 = inttoptr i64 %d.0 to {%Hp,i64**,i64*} (%Hp, i64**, i64*)*
+ %t.2 = call cc101 {%Hp,i64**,i64*} %nentry.0(%Hp %hp.0, i64** %globasp.1, i64* %n.0)
+ %hp.1 = extractvalue {%Hp,i64**,i64*} %t.2, 0
+ %globasp.2 = extractvalue {%Hp,i64**,i64*} %t.2, 1
+ %n.1 = extractvalue {%Hp,i64**,i64*} %t.2, 2
%globasp.3 = call i64** @_pop_global_astack(i64** %asp.0, i64** %aspstart, i64** %globasp.2)
store i64* %n.1, i64** %asp.1 ; TODO this may not be needed?
- %r.2 = insertvalue {i64*,i64**} undef, i64* %hp.1, 0
- %r.3 = insertvalue {i64*,i64**} %r.2, i64** %globasp.3, 1
- ret {i64*,i64**} %r.3
+ %r.2 = insertvalue {%Hp,i64**} undef, %Hp %hp.1, 0
+ %r.3 = insertvalue {%Hp,i64**} %r.2, i64** %globasp.3, 1
+ ret {%Hp,i64**} %r.3
}
define private i64* @ltI(i64* %bsp.0) #0 {