xref: /inferno-os/libkern/div-thumb.s (revision aee7f58dfcd519d45482e45ab1ce6026c846dc21)
1*aee7f58dSforsythQ	= 0
2*aee7f58dSforsythN	= 1
3*aee7f58dSforsythD	= 2
4*aee7f58dSforsythCC	= 3
5*aee7f58dSforsythTMP	= 11
6*aee7f58dSforsyth
7*aee7f58dSforsythTEXT	save<>(SB), 1, $0
8*aee7f58dSforsyth	MOVW	R(Q), 0(FP)
9*aee7f58dSforsyth	MOVW	R(N), 4(FP)
10*aee7f58dSforsyth	MOVW	R(D), 8(FP)
11*aee7f58dSforsyth	MOVW	R(CC), 12(FP)
12*aee7f58dSforsyth
13*aee7f58dSforsyth	MOVW	R(TMP), R(Q)		/* numerator */
14*aee7f58dSforsyth	MOVW	20(FP), R(D)		/* denominator */
15*aee7f58dSforsyth	CMP	$0, R(D)
16*aee7f58dSforsyth	BNE	s1
17*aee7f58dSforsyth	SWI		0
18*aee7f58dSforsyth/*	MOVW	-1(R(D)), R(TMP)	/* divide by zero fault */
19*aee7f58dSforsyths1:	RET
20*aee7f58dSforsyth
21*aee7f58dSforsythTEXT	rest<>(SB), 1, $0
22*aee7f58dSforsyth	MOVW	0(FP), R(Q)
23*aee7f58dSforsyth	MOVW	4(FP), R(N)
24*aee7f58dSforsyth	MOVW	8(FP), R(D)
25*aee7f58dSforsyth	MOVW	12(FP), R(CC)
26*aee7f58dSforsyth/*
27*aee7f58dSforsyth * return to caller
28*aee7f58dSforsyth * of rest<>
29*aee7f58dSforsyth */
30*aee7f58dSforsyth	MOVW	0(R13), R14
31*aee7f58dSforsyth	ADD	$20, R13
32*aee7f58dSforsyth	B	(R14)
33*aee7f58dSforsyth
34*aee7f58dSforsythTEXT	div<>(SB), 1, $0
35*aee7f58dSforsyth	MOVW	$32, R(CC)
36*aee7f58dSforsyth/*
37*aee7f58dSforsyth * skip zeros 8-at-a-time
38*aee7f58dSforsyth */
39*aee7f58dSforsythe1:
40*aee7f58dSforsyth	AND.S	$(0xff<<24),R(Q), R(N)
41*aee7f58dSforsyth	BNE	e2
42*aee7f58dSforsyth	SLL	$8, R(Q)
43*aee7f58dSforsyth	SUB.S	$8, R(CC)
44*aee7f58dSforsyth	BNE	e1
45*aee7f58dSforsyth	RET
46*aee7f58dSforsythe2:
47*aee7f58dSforsyth	MOVW	$0, R(N)
48*aee7f58dSforsyth
49*aee7f58dSforsythloop:
50*aee7f58dSforsyth/*
51*aee7f58dSforsyth * shift R(N||Q) left one
52*aee7f58dSforsyth */
53*aee7f58dSforsyth	SLL	$1, R(N)
54*aee7f58dSforsyth	CMP	$0, R(Q)
55*aee7f58dSforsyth	ORR.LT	$1, R(N)
56*aee7f58dSforsyth	SLL	$1, R(Q)
57*aee7f58dSforsyth
58*aee7f58dSforsyth/*
59*aee7f58dSforsyth * compare numerator to denominator
60*aee7f58dSforsyth * if less, subtract and set quotent bit
61*aee7f58dSforsyth */
62*aee7f58dSforsyth	CMP	R(D), R(N)
63*aee7f58dSforsyth	ORR.HS	$1, R(Q)
64*aee7f58dSforsyth	SUB.HS	R(D), R(N)
65*aee7f58dSforsyth	SUB.S	$1, R(CC)
66*aee7f58dSforsyth	BNE	loop
67*aee7f58dSforsyth	RET
68*aee7f58dSforsyth
69*aee7f58dSforsythTEXT	_div(SB), 1, $16
70*aee7f58dSforsyth	BL	save<>(SB)
71*aee7f58dSforsyth	CMP	$0, R(Q)
72*aee7f58dSforsyth	BGE	d1
73*aee7f58dSforsyth	RSB	$0, R(Q), R(Q)
74*aee7f58dSforsyth	CMP	$0, R(D)
75*aee7f58dSforsyth	BGE	d2
76*aee7f58dSforsyth	RSB	$0, R(D), R(D)
77*aee7f58dSforsythd0:
78*aee7f58dSforsyth	BL	div<>(SB)		/* none/both neg */
79*aee7f58dSforsyth	MOVW	R(Q), R(TMP)
80*aee7f58dSforsyth	B	out
81*aee7f58dSforsythd1:
82*aee7f58dSforsyth	CMP	$0, R(D)
83*aee7f58dSforsyth	BGE	d0
84*aee7f58dSforsyth	RSB	$0, R(D), R(D)
85*aee7f58dSforsythd2:
86*aee7f58dSforsyth	BL	div<>(SB)		/* one neg */
87*aee7f58dSforsyth	RSB	$0, R(Q), R(TMP)
88*aee7f58dSforsyth	B	out
89*aee7f58dSforsyth
90*aee7f58dSforsythTEXT	_mod(SB), 1, $16
91*aee7f58dSforsyth	BL	save<>(SB)
92*aee7f58dSforsyth	CMP	$0, R(D)
93*aee7f58dSforsyth	RSB.LT	$0, R(D), R(D)
94*aee7f58dSforsyth	CMP	$0, R(Q)
95*aee7f58dSforsyth	BGE	m1
96*aee7f58dSforsyth	RSB	$0, R(Q), R(Q)
97*aee7f58dSforsyth	BL	div<>(SB)		/* neg numerator */
98*aee7f58dSforsyth	RSB	$0, R(N), R(TMP)
99*aee7f58dSforsyth	B	out
100*aee7f58dSforsythm1:
101*aee7f58dSforsyth	BL	div<>(SB)		/* pos numerator */
102*aee7f58dSforsyth	MOVW	R(N), R(TMP)
103*aee7f58dSforsyth	B	out
104*aee7f58dSforsyth
105*aee7f58dSforsythTEXT	_divu(SB), 1, $16
106*aee7f58dSforsyth	BL	save<>(SB)
107*aee7f58dSforsyth	BL	div<>(SB)
108*aee7f58dSforsyth	MOVW	R(Q), R(TMP)
109*aee7f58dSforsyth	B	out
110*aee7f58dSforsyth
111*aee7f58dSforsythTEXT	_modu(SB), 1, $16
112*aee7f58dSforsyth	BL	save<>(SB)
113*aee7f58dSforsyth	BL	div<>(SB)
114*aee7f58dSforsyth	MOVW	R(N), R(TMP)
115*aee7f58dSforsyth	B	out
116*aee7f58dSforsyth
117*aee7f58dSforsythout:
118*aee7f58dSforsyth	BL	rest<>(SB)
119*aee7f58dSforsyth	B	out
120