arit.c revision 1.1.1.7 1 1.1 mrg /* Signed and unsigned multiplication and division and modulus for CRIS.
2 1.1 mrg Contributed by Axis Communications.
3 1.1 mrg Written by Hans-Peter Nilsson <hp (at) axis.se>, c:a 1992.
4 1.1 mrg
5 1.1.1.7 mrg Copyright (C) 1998-2020 Free Software Foundation, Inc.
6 1.1 mrg
7 1.1 mrg This file is part of GCC.
8 1.1 mrg
9 1.1 mrg GCC is free software; you can redistribute it and/or modify it
10 1.1 mrg under the terms of the GNU General Public License as published by the
11 1.1 mrg Free Software Foundation; either version 3, or (at your option) any
12 1.1 mrg later version.
13 1.1 mrg
14 1.1 mrg This file is distributed in the hope that it will be useful, but
15 1.1 mrg WITHOUT ANY WARRANTY; without even the implied warranty of
16 1.1 mrg MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17 1.1 mrg General Public License for more details.
18 1.1 mrg
19 1.1 mrg Under Section 7 of GPL version 3, you are granted additional
20 1.1 mrg permissions described in the GCC Runtime Library Exception, version
21 1.1 mrg 3.1, as published by the Free Software Foundation.
22 1.1 mrg
23 1.1 mrg You should have received a copy of the GNU General Public License and
24 1.1 mrg a copy of the GCC Runtime Library Exception along with this program;
25 1.1 mrg see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
26 1.1 mrg <http://www.gnu.org/licenses/>. */
27 1.1 mrg
28 1.1 mrg
29 1.1 mrg /* Note that we provide prototypes for all "const" functions, to attach
30 1.1 mrg the const attribute. This is necessary in 2.7.2 - adding the
31 1.1 mrg attribute to the function *definition* is a syntax error.
32 1.1 mrg This did not work with e.g. 2.1; back then, the return type had to
33 1.1 mrg be "const". */
34 1.1 mrg
35 1.1 mrg #include "config.h"
36 1.1 mrg
37 1.1 mrg #if defined (__CRIS_arch_version) && __CRIS_arch_version >= 3
38 1.1 mrg #define LZ(v) __builtin_clz (v)
39 1.1 mrg #endif
40 1.1 mrg
41 1.1.1.2 mrg /* In (at least) the 4.7 series, GCC doesn't automatically choose the
42 1.1.1.2 mrg most optimal strategy, possibly related to insufficient modelling of
43 1.1.1.2 mrg delay-slot costs. */
44 1.1.1.2 mrg #if defined (__CRIS_arch_version) && __CRIS_arch_version >= 10
45 1.1.1.2 mrg #define SIGNMULT(s, a) ((s) * (a)) /* Cheap multiplication, better than branch. */
46 1.1.1.2 mrg #else
47 1.1.1.2 mrg #define SIGNMULT(s, a) ((s) < 0 ? -(a) : (a)) /* Branches are still better. */
48 1.1.1.2 mrg #endif
49 1.1 mrg
50 1.1 mrg #if defined (L_udivsi3) || defined (L_divsi3) || defined (L_umodsi3) \
51 1.1 mrg || defined (L_modsi3)
52 1.1 mrg /* Result type of divmod worker function. */
53 1.1 mrg struct quot_rem
54 1.1 mrg {
55 1.1 mrg long quot;
56 1.1 mrg long rem;
57 1.1 mrg };
58 1.1 mrg
59 1.1 mrg /* This is the worker function for div and mod. It is inlined into the
60 1.1 mrg respective library function. Parameter A must have bit 31 == 0. */
61 1.1 mrg
62 1.1 mrg static __inline__ struct quot_rem
63 1.1 mrg do_31div (unsigned long a, unsigned long b)
64 1.1 mrg __attribute__ ((__const__, __always_inline__));
65 1.1 mrg
66 1.1 mrg static __inline__ struct quot_rem
67 1.1 mrg do_31div (unsigned long a, unsigned long b)
68 1.1 mrg {
69 1.1 mrg /* Adjust operands and result if a is 31 bits. */
70 1.1 mrg long extra = 0;
71 1.1 mrg int quot_digits = 0;
72 1.1 mrg
73 1.1 mrg if (b == 0)
74 1.1 mrg {
75 1.1 mrg struct quot_rem ret;
76 1.1 mrg ret.quot = 0xffffffff;
77 1.1 mrg ret.rem = 0xffffffff;
78 1.1 mrg return ret;
79 1.1 mrg }
80 1.1 mrg
81 1.1 mrg if (a < b)
82 1.1 mrg return (struct quot_rem) { 0, a };
83 1.1 mrg
84 1.1 mrg #ifdef LZ
85 1.1 mrg if (b <= a)
86 1.1 mrg {
87 1.1 mrg quot_digits = LZ (b) - LZ (a);
88 1.1 mrg quot_digits += (a >= (b << quot_digits));
89 1.1 mrg b <<= quot_digits;
90 1.1 mrg }
91 1.1 mrg #else
92 1.1 mrg while (b <= a)
93 1.1 mrg {
94 1.1 mrg b <<= 1;
95 1.1 mrg quot_digits++;
96 1.1 mrg }
97 1.1 mrg #endif
98 1.1 mrg
99 1.1 mrg /* Is a 31 bits? Note that bit 31 is handled by the caller. */
100 1.1 mrg if (a & 0x40000000)
101 1.1 mrg {
102 1.1 mrg /* Then make b:s highest bit max 0x40000000, because it must have
103 1.1 mrg been 0x80000000 to be 1 bit higher than a. */
104 1.1 mrg b >>= 1;
105 1.1 mrg
106 1.1 mrg /* Adjust a to be maximum 0x3fffffff, i.e. two upper bits zero. */
107 1.1 mrg if (a >= b)
108 1.1 mrg {
109 1.1 mrg a -= b;
110 1.1 mrg extra = 1 << (quot_digits - 1);
111 1.1 mrg }
112 1.1 mrg else
113 1.1 mrg {
114 1.1 mrg a -= b >> 1;
115 1.1 mrg
116 1.1 mrg /* Remember that we adjusted a by subtracting b * 2 ** Something. */
117 1.1 mrg extra = 1 << quot_digits;
118 1.1 mrg }
119 1.1 mrg
120 1.1 mrg /* The number of quotient digits will be one less, because
121 1.1 mrg we just adjusted b. */
122 1.1 mrg quot_digits--;
123 1.1 mrg }
124 1.1 mrg
125 1.1 mrg /* Now do the division part. */
126 1.1 mrg
127 1.1 mrg /* Subtract b and add ones to the right when a >= b
128 1.1 mrg i.e. "a - (b - 1) == (a - b) + 1". */
129 1.1 mrg b--;
130 1.1 mrg
131 1.1.1.7 mrg #define DS __asm__ ("dstep %2,%0" : "=r" (a) : "0" (a), "r" (b)); \
132 1.1.1.7 mrg __attribute__ ((__fallthrough__))
133 1.1 mrg
134 1.1 mrg switch (quot_digits)
135 1.1 mrg {
136 1.1 mrg case 32: DS; case 31: DS; case 30: DS; case 29: DS;
137 1.1 mrg case 28: DS; case 27: DS; case 26: DS; case 25: DS;
138 1.1 mrg case 24: DS; case 23: DS; case 22: DS; case 21: DS;
139 1.1 mrg case 20: DS; case 19: DS; case 18: DS; case 17: DS;
140 1.1 mrg case 16: DS; case 15: DS; case 14: DS; case 13: DS;
141 1.1 mrg case 12: DS; case 11: DS; case 10: DS; case 9: DS;
142 1.1 mrg case 8: DS; case 7: DS; case 6: DS; case 5: DS;
143 1.1 mrg case 4: DS; case 3: DS; case 2: DS; case 1: DS;
144 1.1 mrg case 0:;
145 1.1 mrg }
146 1.1 mrg
147 1.1 mrg {
148 1.1 mrg struct quot_rem ret;
149 1.1 mrg ret.quot = (a & ((1 << quot_digits) - 1)) + extra;
150 1.1 mrg ret.rem = a >> quot_digits;
151 1.1 mrg return ret;
152 1.1 mrg }
153 1.1 mrg }
154 1.1 mrg
155 1.1 mrg #ifdef L_udivsi3
156 1.1 mrg unsigned long
157 1.1 mrg __Udiv (unsigned long a, unsigned long b) __attribute__ ((__const__));
158 1.1 mrg
159 1.1 mrg unsigned long
160 1.1 mrg __Udiv (unsigned long a, unsigned long b)
161 1.1 mrg {
162 1.1 mrg long extra = 0;
163 1.1 mrg
164 1.1 mrg /* Adjust operands and result, if a and/or b is 32 bits. */
165 1.1 mrg /* Effectively: b & 0x80000000. */
166 1.1 mrg if ((long) b < 0)
167 1.1 mrg return a >= b;
168 1.1 mrg
169 1.1 mrg /* Effectively: a & 0x80000000. */
170 1.1 mrg if ((long) a < 0)
171 1.1 mrg {
172 1.1 mrg int tmp = 0;
173 1.1 mrg
174 1.1 mrg if (b == 0)
175 1.1 mrg return 0xffffffff;
176 1.1 mrg #ifdef LZ
177 1.1 mrg tmp = LZ (b);
178 1.1 mrg #else
179 1.1 mrg for (tmp = 31; (((long) b & (1 << tmp)) == 0); tmp--)
180 1.1 mrg ;
181 1.1 mrg
182 1.1 mrg tmp = 31 - tmp;
183 1.1 mrg #endif
184 1.1 mrg
185 1.1 mrg if ((b << tmp) > a)
186 1.1 mrg {
187 1.1 mrg extra = 1 << (tmp-1);
188 1.1 mrg a -= b << (tmp - 1);
189 1.1 mrg }
190 1.1 mrg else
191 1.1 mrg {
192 1.1 mrg extra = 1 << tmp;
193 1.1 mrg a -= b << tmp;
194 1.1 mrg }
195 1.1 mrg }
196 1.1 mrg
197 1.1 mrg return do_31div (a, b).quot+extra;
198 1.1 mrg }
199 1.1 mrg #endif /* L_udivsi3 */
200 1.1 mrg
201 1.1 mrg #ifdef L_divsi3
202 1.1 mrg long
203 1.1 mrg __Div (long a, long b) __attribute__ ((__const__));
204 1.1 mrg
205 1.1 mrg long
206 1.1 mrg __Div (long a, long b)
207 1.1 mrg {
208 1.1 mrg long extra = 0;
209 1.1 mrg long sign = (b < 0) ? -1 : 1;
210 1.1.1.2 mrg long res;
211 1.1 mrg
212 1.1 mrg /* We need to handle a == -2147483648 as expected and must while
213 1.1 mrg doing that avoid producing a sequence like "abs (a) < 0" as GCC
214 1.1 mrg may optimize out the test. That sequence may not be obvious as
215 1.1 mrg we call inline functions. Testing for a being negative and
216 1.1 mrg handling (presumably much rarer than positive) enables us to get
217 1.1 mrg a bit of optimization for an (accumulated) reduction of the
218 1.1 mrg penalty of the 0x80000000 special-case. */
219 1.1 mrg if (a < 0)
220 1.1 mrg {
221 1.1 mrg sign = -sign;
222 1.1 mrg
223 1.1 mrg if ((a & 0x7fffffff) == 0)
224 1.1 mrg {
225 1.1 mrg /* We're at 0x80000000. Tread carefully. */
226 1.1.1.2 mrg a -= SIGNMULT (sign, b);
227 1.1 mrg extra = sign;
228 1.1 mrg }
229 1.1 mrg a = -a;
230 1.1 mrg }
231 1.1 mrg
232 1.1.1.2 mrg res = do_31div (a, __builtin_labs (b)).quot;
233 1.1.1.2 mrg return SIGNMULT (sign, res) + extra;
234 1.1 mrg }
235 1.1 mrg #endif /* L_divsi3 */
236 1.1 mrg
237 1.1 mrg
238 1.1 mrg #ifdef L_umodsi3
239 1.1 mrg unsigned long
240 1.1 mrg __Umod (unsigned long a, unsigned long b) __attribute__ ((__const__));
241 1.1 mrg
242 1.1 mrg unsigned long
243 1.1 mrg __Umod (unsigned long a, unsigned long b)
244 1.1 mrg {
245 1.1 mrg /* Adjust operands and result if a and/or b is 32 bits. */
246 1.1 mrg if ((long) b < 0)
247 1.1 mrg return a >= b ? a - b : a;
248 1.1 mrg
249 1.1 mrg if ((long) a < 0)
250 1.1 mrg {
251 1.1 mrg int tmp = 0;
252 1.1 mrg
253 1.1 mrg if (b == 0)
254 1.1 mrg return a;
255 1.1 mrg #ifdef LZ
256 1.1 mrg tmp = LZ (b);
257 1.1 mrg #else
258 1.1 mrg for (tmp = 31; (((long) b & (1 << tmp)) == 0); tmp--)
259 1.1 mrg ;
260 1.1 mrg tmp = 31 - tmp;
261 1.1 mrg #endif
262 1.1 mrg
263 1.1 mrg if ((b << tmp) > a)
264 1.1 mrg {
265 1.1 mrg a -= b << (tmp - 1);
266 1.1 mrg }
267 1.1 mrg else
268 1.1 mrg {
269 1.1 mrg a -= b << tmp;
270 1.1 mrg }
271 1.1 mrg }
272 1.1 mrg
273 1.1 mrg return do_31div (a, b).rem;
274 1.1 mrg }
275 1.1 mrg #endif /* L_umodsi3 */
276 1.1 mrg
277 1.1 mrg #ifdef L_modsi3
278 1.1 mrg long
279 1.1 mrg __Mod (long a, long b) __attribute__ ((__const__));
280 1.1 mrg
281 1.1 mrg long
282 1.1 mrg __Mod (long a, long b)
283 1.1 mrg {
284 1.1 mrg long sign = 1;
285 1.1.1.2 mrg long res;
286 1.1 mrg
287 1.1 mrg /* We need to handle a == -2147483648 as expected and must while
288 1.1 mrg doing that avoid producing a sequence like "abs (a) < 0" as GCC
289 1.1 mrg may optimize out the test. That sequence may not be obvious as
290 1.1 mrg we call inline functions. Testing for a being negative and
291 1.1 mrg handling (presumably much rarer than positive) enables us to get
292 1.1 mrg a bit of optimization for an (accumulated) reduction of the
293 1.1 mrg penalty of the 0x80000000 special-case. */
294 1.1 mrg if (a < 0)
295 1.1 mrg {
296 1.1 mrg sign = -1;
297 1.1 mrg if ((a & 0x7fffffff) == 0)
298 1.1 mrg /* We're at 0x80000000. Tread carefully. */
299 1.1 mrg a += __builtin_labs (b);
300 1.1 mrg a = -a;
301 1.1 mrg }
302 1.1 mrg
303 1.1.1.2 mrg res = do_31div (a, __builtin_labs (b)).rem;
304 1.1.1.2 mrg return SIGNMULT (sign, res);
305 1.1 mrg }
306 1.1 mrg #endif /* L_modsi3 */
307 1.1 mrg #endif /* L_udivsi3 || L_divsi3 || L_umodsi3 || L_modsi3 */
308 1.1 mrg
309 1.1 mrg /*
310 1.1 mrg * Local variables:
311 1.1 mrg * eval: (c-set-style "gnu")
312 1.1 mrg * indent-tabs-mode: t
313 1.1 mrg * End:
314 1.1 mrg */
315