This repository has been archived by the owner on Jan 5, 2019. It is now read-only.
-
Notifications
You must be signed in to change notification settings - Fork 38
/
Copy pathADD.wast
53 lines (46 loc) · 1.98 KB
/
ADD.wast
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
(func $ADD
(local $sp i32)
(local $a i64)
(local $c i64)
(local $d i64)
(local $carry i64)
(set_local $sp (get_global $sp))
;; d c b a
;; pop the stack
(set_local $a (i64.load (i32.add (get_local $sp) (i32.const 24))))
(set_local $c (i64.load (i32.add (get_local $sp) (i32.const 8))))
(set_local $d (i64.load (get_local $sp)))
;; decement the stack pointer
(set_local $sp (i32.sub (get_local $sp) (i32.const 8)))
;; d
(set_local $carry (i64.add (get_local $d) (i64.load (i32.sub (get_local $sp) (i32.const 24)))))
;; save d to mem
(i64.store (i32.sub (get_local $sp) (i32.const 24)) (get_local $carry))
;; check for overflow
(set_local $carry (i64.extend_u/i32 (i64.lt_u (get_local $carry) (get_local $d))))
;; c use $d as reg
(set_local $d (i64.add (i64.load (i32.sub (get_local $sp) (i32.const 16))) (get_local $carry)))
(set_local $carry (i64.extend_u/i32 (i64.lt_u (get_local $d) (get_local $carry))))
(set_local $d (i64.add (get_local $c) (get_local $d)))
;; store the result
(i64.store (i32.sub (get_local $sp) (i32.const 16)) (get_local $d))
;; check overflow
(set_local $carry (i64.or (i64.extend_u/i32 (i64.lt_u (get_local $d) (get_local $c))) (get_local $carry)))
;; b
;; add carry
(set_local $d (i64.add (i64.load (i32.sub (get_local $sp) (i32.const 8))) (get_local $carry)))
(set_local $carry (i64.extend_u/i32 (i64.lt_u (get_local $d) (get_local $carry))))
;; use reg c
(set_local $c (i64.load (i32.add (get_local $sp) (i32.const 24))))
(set_local $d (i64.add (get_local $c) (get_local $d)))
(i64.store (i32.sub (get_local $sp) (i32.const 8)) (get_local $d))
;; a
(i64.store (get_local $sp)
(i64.add ;; add a
(get_local $a)
(i64.add
(i64.load (get_local $sp)) ;; load the operand
(i64.or ;; carry
(i64.extend_u/i32 (i64.lt_u (get_local $d) (get_local $c)))
(get_local $carry)))))
)