Subversion Repositories planix.SVN

Rev

Rev 2 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
2 - 1
/*
2
 *	ulong
3
 *	_udiv(ulong num, ulong den)
4
 *	{
5
 *		int i;
6
 *		ulong quo;
7
 *
8
 *		if(den == 0)
9
 *			*(ulong*)-1 = 0;
10
 *		quo = num;
11
 *		if(quo > 1<<(32-1))
12
 *			quo = 1<<(32-1);
13
 *		for(i=0; den<quo; i++)
14
 *			den <<= 1;
15
 *		quo = 0;
16
 *		for(; i>=0; i--) {
17
 *			quo <<= 1;
18
 *			if(num >= den) {
19
 *				num -= den;
20
 *				quo |= 1;
21
 *			}
22
 *			den >>= 1;
23
 *		}
24
 *		return quo::num;
25
 *	}
26
 */
27
 
28
#define	NOPROF	1
29
 
30
/*
31
 * calling sequence:
32
 *	num: 4(R1)
33
 *	den: 8(R1)
34
 * returns
35
 *	quo: 4(R1)
36
 *	rem: 8(R1)
37
 */
38
TEXT	_udivmod(SB), NOPROF, $-4
39
 
40
	MOVW	$(1<<31), R11
41
	MOVW	4(R1), R13	/* numerator */
42
	MOVW	8(R1), R10	/* denominator */
43
	CMP	R10, R0
44
	BNE	udm20
45
	MOVW	R0, -1(R0)	/* fault -- divide by zero */
46
udm20:
47
	MOVW	R13, R12
48
	CMP	R13, R11
49
	BLEU	udm34
50
	MOVW	R11, R12
51
udm34:
52
	MOVW	R0, R11
53
udm38:
54
	CMP	R10, R12
55
	BCC	udm54
56
	SLL	$1, R10
57
	ADD	$1, R11
58
	BA	udm38
59
udm54:
60
	MOVW	R0, R12
61
udm58:
62
	CMP	R11, R0
63
	BL	udm8c
64
	SLL	$1, R12
65
	CMP	R13, R10
66
	BCS	udm7c
67
	SUB	R10, R13
68
	OR	$1, R12
69
udm7c:
70
	SRL	$1, R10
71
	SUB	$1, R11
72
	BA	udm58
73
udm8c:
74
	MOVW	R12, 4(R1)	/* quotent */
75
	MOVW	R13, 8(R1)	/* remainder */
76
	JMPL	8(R15)
77
 
78
/*
79
 * save working registers
80
 * and bring in num/den parameters
81
 */
82
TEXT	_unsarg(SB), NOPROF, $-4
83
	MOVW	R10, 12(R1)
84
	MOVW	R11, 16(R1)
85
	MOVW	R12, 20(R1)
86
	MOVW	R13, 24(R1)
87
 
88
	MOVW	R14, 4(R1)
89
	MOVW	32(R1), R14
90
	MOVW	R14, 8(R1)
91
 
92
	JMPL	8(R15)
93
 
94
/*
95
 * save working registers
96
 * and bring in absolute value
97
 * of num/den parameters
98
 */
99
TEXT	_absarg(SB), NOPROF, $-4
100
	MOVW	R10, 12(R1)
101
	MOVW	R11, 16(R1)
102
	MOVW	R12, 20(R1)
103
	MOVW	R13, 24(R1)
104
 
105
	MOVW	R14, 28(R1)
106
	CMP	R14, R0
107
	BGE	ab1
108
	SUB	R14, R0, R14
109
ab1:
110
	MOVW	R14, 4(R1)	/* numerator */
111
 
112
	MOVW	32(R1), R14
113
	CMP	R14, R0
114
	BGE	ab2
115
	SUB	R14, R0, R14
116
ab2:
117
	MOVW	R14, 8(R1)	/* denominator */
118
	JMPL	8(R15)
119
 
120
/*
121
 * restore registers and
122
 * return to original caller
123
 * answer is in R14
124
 */
125
TEXT	_retarg(SB), NOPROF, $-4
126
	MOVW	12(R1), R10
127
	MOVW	16(R1), R11
128
	MOVW	20(R1), R12
129
	MOVW	24(R1), R13
130
	MOVW	0(R1), R15
131
 
132
	ADD	$28, R1
133
	JMP	8(R15)		/* back to main sequence */
134
 
135
/*
136
 * calling sequence
137
 *	num: R14
138
 *	den: 8(R1)
139
 * returns
140
 *	quo: R14
141
 */
142
TEXT	_div(SB), NOPROF, $-4
143
	SUB	$28, R1		/* 4 reg save, 2 parameters, link */
144
	MOVW	R15, 0(R1)
145
 
146
	JMPL	_absarg(SB)
147
	JMPL	_udivmod(SB)
148
	MOVW	4(R1), R14
149
 
150
	MOVW	28(R1), R10	/* clean up the sign */
151
	MOVW	32(R1), R11
152
	XORCC	R11, R10, R0
153
	BGE	div1
154
	SUB	R14, R0, R14
155
div1:
156
 
157
	JMPL	_retarg(SB)
158
	JMP	8(R15)		/* not executed */
159
 
160
/*
161
 * calling sequence
162
 *	num: R14
163
 *	den: 8(R1)
164
 * returns
165
 *	quo: R14
166
 */
167
TEXT	_divl(SB), NOPROF, $-4
168
	SUB	$((4+2+1)*4), R1	/* 4 reg save, 2 parameters, link */
169
	MOVW	R15, 0(R1)
170
 
171
	JMPL	_unsarg(SB)
172
	JMPL	_udivmod(SB)
173
	MOVW	4(R1), R14
174
 
175
	JMPL	_retarg(SB)
176
	JMP	8(R15)		/* not executed */
177
 
178
/*
179
 * calling sequence
180
 *	num: R14
181
 *	den: 8(R1)
182
 * returns
183
 *	rem: R14
184
 */
185
TEXT	_mod(SB), NOPROF, $-4
186
	SUB	$28, R1		/* 4 reg save, 2 parameters, link */
187
 
188
	MOVW	R15, 0(R1)
189
	JMPL	_absarg(SB)
190
	JMPL	_udivmod(SB)
191
	MOVW	8(R1), R14
192
 
193
	MOVW	28(R1), R10	/* clean up the sign */
194
	CMP	R10, R0
195
	BGE	mod1
196
	SUB	R14, R0, R14
197
mod1:
198
 
199
	JMPL	_retarg(SB)
200
	JMP	8(R15)		/* not executed */
201
 
202
/*
203
 * calling sequence
204
 *	num: R14
205
 *	den: 8(R1)
206
 * returns
207
 *	rem: R14
208
 */
209
TEXT	_modl(SB), NOPROF, $-4
210
	SUB	$28, R1		/* 4 reg save, 2 parameters, link */
211
 
212
 
213
	MOVW	R15, 0(R1)
214
	JMPL	_unsarg(SB)
215
	JMPL	_udivmod(SB)
216
	MOVW	8(R1), R14
217
 
218
	JMPL	_retarg(SB)
219
	JMP	8(R15)		/* not executed */
220
 
221
/*
222
 * special calling sequence:
223
 *	arg1 in R14
224
 *	arg2 in 4(R1),    will save R9
225
 *	nothing in 0(R1), will save R8
226
 * 	result in R14
227
 */
228
TEXT	_mul+0(SB), NOPROF, $-4
229
 
230
	/*
231
	 * exchange stack and registers
232
	 */
233
	MOVW	R8, 0(R1)
234
	MOVW	4(R1), R8
235
	MOVW	R9, 4(R1)
236
 
237
	CMP	R14, R8
238
	BLE	mul1
239
	MOVW	R14, R9
240
	MOVW	R8, R14
241
	MOVW	R9, R8
242
mul1:
243
	MOVW	R14, Y
244
	ANDNCC	$0xFFF, R14, R0
245
	BE	mul_shortway
246
	ANDCC	R0, R0, R9	/* zero partial product and clear N and V cond's */
247
 
248
	/* long multiply */
249
	MULSCC	R8, R9, R9		/* 0 */
250
	MULSCC	R8, R9, R9		/* 1 */
251
	MULSCC	R8, R9, R9		/* 2 */
252
	MULSCC	R8, R9, R9		/* 3 */
253
	MULSCC	R8, R9, R9		/* 4 */
254
	MULSCC	R8, R9, R9		/* 5 */
255
	MULSCC	R8, R9, R9		/* 6 */
256
	MULSCC	R8, R9, R9		/* 7 */
257
	MULSCC	R8, R9, R9		/* 8 */
258
	MULSCC	R8, R9, R9		/* 9 */
259
	MULSCC	R8, R9, R9		/* 10 */
260
	MULSCC	R8, R9, R9		/* 11 */
261
	MULSCC	R8, R9, R9		/* 12 */
262
	MULSCC	R8, R9, R9		/* 13 */
263
	MULSCC	R8, R9, R9		/* 14 */
264
	MULSCC	R8, R9, R9		/* 15 */
265
	MULSCC	R8, R9, R9		/* 16 */
266
	MULSCC	R8, R9, R9		/* 17 */
267
	MULSCC	R8, R9, R9		/* 18 */
268
	MULSCC	R8, R9, R9		/* 19 */
269
	MULSCC	R8, R9, R9		/* 20 */
270
	MULSCC	R8, R9, R9		/* 21 */
271
	MULSCC	R8, R9, R9		/* 22 */
272
	MULSCC	R8, R9, R9		/* 23 */
273
	MULSCC	R8, R9, R9		/* 24 */
274
	MULSCC	R8, R9, R9		/* 25 */
275
	MULSCC	R8, R9, R9		/* 26 */
276
	MULSCC	R8, R9, R9		/* 27 */
277
	MULSCC	R8, R9, R9		/* 28 */
278
	MULSCC	R8, R9, R9		/* 29 */
279
	MULSCC	R8, R9, R9		/* 30 */
280
	MULSCC	R8, R9, R9		/* 31 */
281
	MULSCC	R0, R9, R9		/* 32; shift only */
282
 
283
	MOVW	Y, R14			/* get low part */
284
	BA	mul_return
285
 
286
mul_shortway:
287
	ANDCC	R0, R0, R9	/* zero partial product and clear N and V cond's */
288
	MULSCC	R8, R9, R9		/*  0 */
289
	MULSCC	R8, R9, R9		/*  1 */
290
	MULSCC	R8, R9, R9		/*  2 */
291
	MULSCC	R8, R9, R9		/*  3 */
292
	MULSCC	R8, R9, R9		/*  4 */
293
	MULSCC	R8, R9, R9		/*  5 */
294
	MULSCC	R8, R9, R9		/*  6 */
295
	MULSCC	R8, R9, R9		/*  7 */
296
	MULSCC	R8, R9, R9		/*  8 */
297
	MULSCC	R8, R9, R9		/*  9 */
298
	MULSCC	R8, R9, R9		/* 10 */
299
	MULSCC	R8, R9, R9		/* 11 */
300
	MULSCC	R0, R9, R9		/* 12; shift only */
301
 
302
	MOVW	Y, R8
303
	SLL	$12, R9
304
	SRL	$20, R8
305
	OR	R8, R9, R14
306
 
307
mul_return:
308
	MOVW	0(R1), R8
309
	MOVW	4(R1), R9
310
	JMP	8(R15)