;; -*- Mode: Lisp; -*- ;; Unsigned divison (defmacro jc (addr) `(progn (jnc (+ @ 2)) (jmp ,addr))) (defmacro jz (addr) `(progn (jnz (+ @ 2)) (jmp ,addr))) (defmacro shr () `(progn (asr) (and '#x7FFFFFFF))) (:bss) div.x (ds 1) ;dividend and remainder, when done div.y (ds 1) ;divisor div.q (ds 1) div.m (ds 1) div.tmp (ds 1) (:text) div (sto div.ret) (lod '0) (sto div.q) ;q = 0 (lod '1) (sto div.m) ;m = 1 div.L1 ;; while x <= 2y, shift both y and m left ;; and 2y still fits (lod div.y) (and '#x80000000) (jnz div.L2) (lod div.y) (add div.y) (sto div.tmp) (lod div.x) (sub div.tmp) (jc div.L2) ;2y > x (lod div.tmp) (sto div.y) ;y = y + y (lod div.m) (add div.m) (sto div.m) ;m = m + k (jmp div.L1) div.L2 (lod div.x) (sub div.y) (jc div.L3) ;y > x (sto div.x) (lod div.q) (add div.m) (sto div.q) ;q += m div.L3 (lod div.m) (shr) (jz div.done) (sto div.m) ;; (lod div.y) (shr) (sto div.y) (jmp div.L2) div.done (lod div.q) div.ret (jmp @)