annotate libgcc/config/mcore/lib1funcs.S @ 158:494b0b89df80 default tip

...
author Shinji KONO <kono@ie.u-ryukyu.ac.jp>
date Mon, 25 May 2020 18:13:55 +0900
parents 1830386684a0
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
111
kono
parents:
diff changeset
1 /* libgcc routines for the MCore.
145
1830386684a0 gcc-9.2.0
anatofuz
parents: 131
diff changeset
2 Copyright (C) 1993-2020 Free Software Foundation, Inc.
111
kono
parents:
diff changeset
3
kono
parents:
diff changeset
4 This file is part of GCC.
kono
parents:
diff changeset
5
kono
parents:
diff changeset
6 GCC is free software; you can redistribute it and/or modify it
kono
parents:
diff changeset
7 under the terms of the GNU General Public License as published by the
kono
parents:
diff changeset
8 Free Software Foundation; either version 3, or (at your option) any
kono
parents:
diff changeset
9 later version.
kono
parents:
diff changeset
10
kono
parents:
diff changeset
11 This file is distributed in the hope that it will be useful, but
kono
parents:
diff changeset
12 WITHOUT ANY WARRANTY; without even the implied warranty of
kono
parents:
diff changeset
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
kono
parents:
diff changeset
14 General Public License for more details.
kono
parents:
diff changeset
15
kono
parents:
diff changeset
16 Under Section 7 of GPL version 3, you are granted additional
kono
parents:
diff changeset
17 permissions described in the GCC Runtime Library Exception, version
kono
parents:
diff changeset
18 3.1, as published by the Free Software Foundation.
kono
parents:
diff changeset
19
kono
parents:
diff changeset
20 You should have received a copy of the GNU General Public License and
kono
parents:
diff changeset
21 a copy of the GCC Runtime Library Exception along with this program;
kono
parents:
diff changeset
22 see the files COPYING3 and COPYING.RUNTIME respectively. If not, see
kono
parents:
diff changeset
23 <http://www.gnu.org/licenses/>. */
kono
parents:
diff changeset
24
kono
parents:
diff changeset
25 #define CONCAT1(a, b) CONCAT2(a, b)
kono
parents:
diff changeset
26 #define CONCAT2(a, b) a ## b
kono
parents:
diff changeset
27
kono
parents:
diff changeset
28 /* Use the right prefix for global labels. */
kono
parents:
diff changeset
29
kono
parents:
diff changeset
30 #define SYM(x) CONCAT1 (__, x)
kono
parents:
diff changeset
31
kono
parents:
diff changeset
32 #ifdef __ELF__
kono
parents:
diff changeset
33 #define TYPE(x) .type SYM (x),@function
kono
parents:
diff changeset
34 #define SIZE(x) .size SYM (x), . - SYM (x)
kono
parents:
diff changeset
35 #else
kono
parents:
diff changeset
36 #define TYPE(x)
kono
parents:
diff changeset
37 #define SIZE(x)
kono
parents:
diff changeset
38 #endif
kono
parents:
diff changeset
39
kono
parents:
diff changeset
40 .macro FUNC_START name
kono
parents:
diff changeset
41 .text
kono
parents:
diff changeset
42 .globl SYM (\name)
kono
parents:
diff changeset
43 TYPE (\name)
kono
parents:
diff changeset
44 SYM (\name):
kono
parents:
diff changeset
45 .endm
kono
parents:
diff changeset
46
kono
parents:
diff changeset
47 .macro FUNC_END name
kono
parents:
diff changeset
48 SIZE (\name)
kono
parents:
diff changeset
49 .endm
kono
parents:
diff changeset
50
kono
parents:
diff changeset
51 #ifdef L_udivsi3
kono
parents:
diff changeset
52 FUNC_START udiv32
kono
parents:
diff changeset
53 FUNC_START udivsi32
kono
parents:
diff changeset
54
kono
parents:
diff changeset
55 movi r1,0 // r1-r2 form 64 bit dividend
kono
parents:
diff changeset
56 movi r4,1 // r4 is quotient (1 for a sentinel)
kono
parents:
diff changeset
57
kono
parents:
diff changeset
58 cmpnei r3,0 // look for 0 divisor
kono
parents:
diff changeset
59 bt 9f
kono
parents:
diff changeset
60 trap 3 // divide by 0
kono
parents:
diff changeset
61 9:
kono
parents:
diff changeset
62 // control iterations; skip across high order 0 bits in dividend
kono
parents:
diff changeset
63 mov r7,r2
kono
parents:
diff changeset
64 cmpnei r7,0
kono
parents:
diff changeset
65 bt 8f
kono
parents:
diff changeset
66 movi r2,0 // 0 dividend
kono
parents:
diff changeset
67 jmp r15 // quick return
kono
parents:
diff changeset
68 8:
kono
parents:
diff changeset
69 ff1 r7 // figure distance to skip
kono
parents:
diff changeset
70 lsl r4,r7 // move the sentinel along (with 0's behind)
kono
parents:
diff changeset
71 lsl r2,r7 // and the low 32 bits of numerator
kono
parents:
diff changeset
72
kono
parents:
diff changeset
73 // appears to be wrong...
kono
parents:
diff changeset
74 // tested out incorrectly in our OS work...
kono
parents:
diff changeset
75 // mov r7,r3 // looking at divisor
kono
parents:
diff changeset
76 // ff1 r7 // I can move 32-r7 more bits to left.
kono
parents:
diff changeset
77 // addi r7,1 // ok, one short of that...
kono
parents:
diff changeset
78 // mov r1,r2
kono
parents:
diff changeset
79 // lsr r1,r7 // bits that came from low order...
kono
parents:
diff changeset
80 // rsubi r7,31 // r7 == "32-n" == LEFT distance
kono
parents:
diff changeset
81 // addi r7,1 // this is (32-n)
kono
parents:
diff changeset
82 // lsl r4,r7 // fixes the high 32 (quotient)
kono
parents:
diff changeset
83 // lsl r2,r7
kono
parents:
diff changeset
84 // cmpnei r4,0
kono
parents:
diff changeset
85 // bf 4f // the sentinel went away...
kono
parents:
diff changeset
86
kono
parents:
diff changeset
87 // run the remaining bits
kono
parents:
diff changeset
88
kono
parents:
diff changeset
89 1: lslc r2,1 // 1 bit left shift of r1-r2
kono
parents:
diff changeset
90 addc r1,r1
kono
parents:
diff changeset
91 cmphs r1,r3 // upper 32 of dividend >= divisor?
kono
parents:
diff changeset
92 bf 2f
kono
parents:
diff changeset
93 sub r1,r3 // if yes, subtract divisor
kono
parents:
diff changeset
94 2: addc r4,r4 // shift by 1 and count subtracts
kono
parents:
diff changeset
95 bf 1b // if sentinel falls out of quotient, stop
kono
parents:
diff changeset
96
kono
parents:
diff changeset
97 4: mov r2,r4 // return quotient
kono
parents:
diff changeset
98 mov r3,r1 // and piggyback the remainder
kono
parents:
diff changeset
99 jmp r15
kono
parents:
diff changeset
100 FUNC_END udiv32
kono
parents:
diff changeset
101 FUNC_END udivsi32
kono
parents:
diff changeset
102 #endif
kono
parents:
diff changeset
103
kono
parents:
diff changeset
104 #ifdef L_umodsi3
kono
parents:
diff changeset
105 FUNC_START urem32
kono
parents:
diff changeset
106 FUNC_START umodsi3
kono
parents:
diff changeset
107 movi r1,0 // r1-r2 form 64 bit dividend
kono
parents:
diff changeset
108 movi r4,1 // r4 is quotient (1 for a sentinel)
kono
parents:
diff changeset
109 cmpnei r3,0 // look for 0 divisor
kono
parents:
diff changeset
110 bt 9f
kono
parents:
diff changeset
111 trap 3 // divide by 0
kono
parents:
diff changeset
112 9:
kono
parents:
diff changeset
113 // control iterations; skip across high order 0 bits in dividend
kono
parents:
diff changeset
114 mov r7,r2
kono
parents:
diff changeset
115 cmpnei r7,0
kono
parents:
diff changeset
116 bt 8f
kono
parents:
diff changeset
117 movi r2,0 // 0 dividend
kono
parents:
diff changeset
118 jmp r15 // quick return
kono
parents:
diff changeset
119 8:
kono
parents:
diff changeset
120 ff1 r7 // figure distance to skip
kono
parents:
diff changeset
121 lsl r4,r7 // move the sentinel along (with 0's behind)
kono
parents:
diff changeset
122 lsl r2,r7 // and the low 32 bits of numerator
kono
parents:
diff changeset
123
kono
parents:
diff changeset
124 1: lslc r2,1 // 1 bit left shift of r1-r2
kono
parents:
diff changeset
125 addc r1,r1
kono
parents:
diff changeset
126 cmphs r1,r3 // upper 32 of dividend >= divisor?
kono
parents:
diff changeset
127 bf 2f
kono
parents:
diff changeset
128 sub r1,r3 // if yes, subtract divisor
kono
parents:
diff changeset
129 2: addc r4,r4 // shift by 1 and count subtracts
kono
parents:
diff changeset
130 bf 1b // if sentinel falls out of quotient, stop
kono
parents:
diff changeset
131 mov r2,r1 // return remainder
kono
parents:
diff changeset
132 jmp r15
kono
parents:
diff changeset
133 FUNC_END urem32
kono
parents:
diff changeset
134 FUNC_END umodsi3
kono
parents:
diff changeset
135 #endif
kono
parents:
diff changeset
136
kono
parents:
diff changeset
137 #ifdef L_divsi3
kono
parents:
diff changeset
138 FUNC_START div32
kono
parents:
diff changeset
139 FUNC_START divsi3
kono
parents:
diff changeset
140 mov r5,r2 // calc sign of quotient
kono
parents:
diff changeset
141 xor r5,r3
kono
parents:
diff changeset
142 abs r2 // do unsigned divide
kono
parents:
diff changeset
143 abs r3
kono
parents:
diff changeset
144 movi r1,0 // r1-r2 form 64 bit dividend
kono
parents:
diff changeset
145 movi r4,1 // r4 is quotient (1 for a sentinel)
kono
parents:
diff changeset
146 cmpnei r3,0 // look for 0 divisor
kono
parents:
diff changeset
147 bt 9f
kono
parents:
diff changeset
148 trap 3 // divide by 0
kono
parents:
diff changeset
149 9:
kono
parents:
diff changeset
150 // control iterations; skip across high order 0 bits in dividend
kono
parents:
diff changeset
151 mov r7,r2
kono
parents:
diff changeset
152 cmpnei r7,0
kono
parents:
diff changeset
153 bt 8f
kono
parents:
diff changeset
154 movi r2,0 // 0 dividend
kono
parents:
diff changeset
155 jmp r15 // quick return
kono
parents:
diff changeset
156 8:
kono
parents:
diff changeset
157 ff1 r7 // figure distance to skip
kono
parents:
diff changeset
158 lsl r4,r7 // move the sentinel along (with 0's behind)
kono
parents:
diff changeset
159 lsl r2,r7 // and the low 32 bits of numerator
kono
parents:
diff changeset
160
kono
parents:
diff changeset
161 // tested out incorrectly in our OS work...
kono
parents:
diff changeset
162 // mov r7,r3 // looking at divisor
kono
parents:
diff changeset
163 // ff1 r7 // I can move 32-r7 more bits to left.
kono
parents:
diff changeset
164 // addi r7,1 // ok, one short of that...
kono
parents:
diff changeset
165 // mov r1,r2
kono
parents:
diff changeset
166 // lsr r1,r7 // bits that came from low order...
kono
parents:
diff changeset
167 // rsubi r7,31 // r7 == "32-n" == LEFT distance
kono
parents:
diff changeset
168 // addi r7,1 // this is (32-n)
kono
parents:
diff changeset
169 // lsl r4,r7 // fixes the high 32 (quotient)
kono
parents:
diff changeset
170 // lsl r2,r7
kono
parents:
diff changeset
171 // cmpnei r4,0
kono
parents:
diff changeset
172 // bf 4f // the sentinel went away...
kono
parents:
diff changeset
173
kono
parents:
diff changeset
174 // run the remaining bits
kono
parents:
diff changeset
175 1: lslc r2,1 // 1 bit left shift of r1-r2
kono
parents:
diff changeset
176 addc r1,r1
kono
parents:
diff changeset
177 cmphs r1,r3 // upper 32 of dividend >= divisor?
kono
parents:
diff changeset
178 bf 2f
kono
parents:
diff changeset
179 sub r1,r3 // if yes, subtract divisor
kono
parents:
diff changeset
180 2: addc r4,r4 // shift by 1 and count subtracts
kono
parents:
diff changeset
181 bf 1b // if sentinel falls out of quotient, stop
kono
parents:
diff changeset
182
kono
parents:
diff changeset
183 4: mov r2,r4 // return quotient
kono
parents:
diff changeset
184 mov r3,r1 // piggyback the remainder
kono
parents:
diff changeset
185 btsti r5,31 // after adjusting for sign
kono
parents:
diff changeset
186 bf 3f
kono
parents:
diff changeset
187 rsubi r2,0
kono
parents:
diff changeset
188 rsubi r3,0
kono
parents:
diff changeset
189 3: jmp r15
kono
parents:
diff changeset
190 FUNC_END div32
kono
parents:
diff changeset
191 FUNC_END divsi3
kono
parents:
diff changeset
192 #endif
kono
parents:
diff changeset
193
kono
parents:
diff changeset
194 #ifdef L_modsi3
kono
parents:
diff changeset
195 FUNC_START rem32
kono
parents:
diff changeset
196 FUNC_START modsi3
kono
parents:
diff changeset
197 mov r5,r2 // calc sign of remainder
kono
parents:
diff changeset
198 abs r2 // do unsigned divide
kono
parents:
diff changeset
199 abs r3
kono
parents:
diff changeset
200 movi r1,0 // r1-r2 form 64 bit dividend
kono
parents:
diff changeset
201 movi r4,1 // r4 is quotient (1 for a sentinel)
kono
parents:
diff changeset
202 cmpnei r3,0 // look for 0 divisor
kono
parents:
diff changeset
203 bt 9f
kono
parents:
diff changeset
204 trap 3 // divide by 0
kono
parents:
diff changeset
205 9:
kono
parents:
diff changeset
206 // control iterations; skip across high order 0 bits in dividend
kono
parents:
diff changeset
207 mov r7,r2
kono
parents:
diff changeset
208 cmpnei r7,0
kono
parents:
diff changeset
209 bt 8f
kono
parents:
diff changeset
210 movi r2,0 // 0 dividend
kono
parents:
diff changeset
211 jmp r15 // quick return
kono
parents:
diff changeset
212 8:
kono
parents:
diff changeset
213 ff1 r7 // figure distance to skip
kono
parents:
diff changeset
214 lsl r4,r7 // move the sentinel along (with 0's behind)
kono
parents:
diff changeset
215 lsl r2,r7 // and the low 32 bits of numerator
kono
parents:
diff changeset
216
kono
parents:
diff changeset
217 1: lslc r2,1 // 1 bit left shift of r1-r2
kono
parents:
diff changeset
218 addc r1,r1
kono
parents:
diff changeset
219 cmphs r1,r3 // upper 32 of dividend >= divisor?
kono
parents:
diff changeset
220 bf 2f
kono
parents:
diff changeset
221 sub r1,r3 // if yes, subtract divisor
kono
parents:
diff changeset
222 2: addc r4,r4 // shift by 1 and count subtracts
kono
parents:
diff changeset
223 bf 1b // if sentinel falls out of quotient, stop
kono
parents:
diff changeset
224 mov r2,r1 // return remainder
kono
parents:
diff changeset
225 btsti r5,31 // after adjusting for sign
kono
parents:
diff changeset
226 bf 3f
kono
parents:
diff changeset
227 rsubi r2,0
kono
parents:
diff changeset
228 3: jmp r15
kono
parents:
diff changeset
229 FUNC_END rem32
kono
parents:
diff changeset
230 FUNC_END modsi3
kono
parents:
diff changeset
231 #endif
kono
parents:
diff changeset
232
kono
parents:
diff changeset
233
kono
parents:
diff changeset
234 /* GCC expects that {__eq,__ne,__gt,__ge,__le,__lt}{df2,sf2}
kono
parents:
diff changeset
235 will behave as __cmpdf2. So, we stub the implementations to
kono
parents:
diff changeset
236 jump on to __cmpdf2 and __cmpsf2.
kono
parents:
diff changeset
237
kono
parents:
diff changeset
238 All of these shortcircuit the return path so that __cmp{sd}f2
kono
parents:
diff changeset
239 will go directly back to the caller. */
kono
parents:
diff changeset
240
kono
parents:
diff changeset
241 .macro COMPARE_DF_JUMP name
kono
parents:
diff changeset
242 .import SYM (cmpdf2)
kono
parents:
diff changeset
243 FUNC_START \name
kono
parents:
diff changeset
244 jmpi SYM (cmpdf2)
kono
parents:
diff changeset
245 FUNC_END \name
kono
parents:
diff changeset
246 .endm
kono
parents:
diff changeset
247
kono
parents:
diff changeset
248 #ifdef L_eqdf2
kono
parents:
diff changeset
249 COMPARE_DF_JUMP eqdf2
kono
parents:
diff changeset
250 #endif /* L_eqdf2 */
kono
parents:
diff changeset
251
kono
parents:
diff changeset
252 #ifdef L_nedf2
kono
parents:
diff changeset
253 COMPARE_DF_JUMP nedf2
kono
parents:
diff changeset
254 #endif /* L_nedf2 */
kono
parents:
diff changeset
255
kono
parents:
diff changeset
256 #ifdef L_gtdf2
kono
parents:
diff changeset
257 COMPARE_DF_JUMP gtdf2
kono
parents:
diff changeset
258 #endif /* L_gtdf2 */
kono
parents:
diff changeset
259
kono
parents:
diff changeset
260 #ifdef L_gedf2
kono
parents:
diff changeset
261 COMPARE_DF_JUMP gedf2
kono
parents:
diff changeset
262 #endif /* L_gedf2 */
kono
parents:
diff changeset
263
kono
parents:
diff changeset
264 #ifdef L_ltdf2
kono
parents:
diff changeset
265 COMPARE_DF_JUMP ltdf2
kono
parents:
diff changeset
266 #endif /* L_ltdf2 */
kono
parents:
diff changeset
267
kono
parents:
diff changeset
268 #ifdef L_ledf2
kono
parents:
diff changeset
269 COMPARE_DF_JUMP ledf2
kono
parents:
diff changeset
270 #endif /* L_ledf2 */
kono
parents:
diff changeset
271
kono
parents:
diff changeset
272 /* SINGLE PRECISION FLOATING POINT STUBS */
kono
parents:
diff changeset
273
kono
parents:
diff changeset
274 .macro COMPARE_SF_JUMP name
kono
parents:
diff changeset
275 .import SYM (cmpsf2)
kono
parents:
diff changeset
276 FUNC_START \name
kono
parents:
diff changeset
277 jmpi SYM (cmpsf2)
kono
parents:
diff changeset
278 FUNC_END \name
kono
parents:
diff changeset
279 .endm
kono
parents:
diff changeset
280
kono
parents:
diff changeset
281 #ifdef L_eqsf2
kono
parents:
diff changeset
282 COMPARE_SF_JUMP eqsf2
kono
parents:
diff changeset
283 #endif /* L_eqsf2 */
kono
parents:
diff changeset
284
kono
parents:
diff changeset
285 #ifdef L_nesf2
kono
parents:
diff changeset
286 COMPARE_SF_JUMP nesf2
kono
parents:
diff changeset
287 #endif /* L_nesf2 */
kono
parents:
diff changeset
288
kono
parents:
diff changeset
289 #ifdef L_gtsf2
kono
parents:
diff changeset
290 COMPARE_SF_JUMP gtsf2
kono
parents:
diff changeset
291 #endif /* L_gtsf2 */
kono
parents:
diff changeset
292
kono
parents:
diff changeset
293 #ifdef L_gesf2
kono
parents:
diff changeset
294 COMPARE_SF_JUMP __gesf2
kono
parents:
diff changeset
295 #endif /* L_gesf2 */
kono
parents:
diff changeset
296
kono
parents:
diff changeset
297 #ifdef L_ltsf2
kono
parents:
diff changeset
298 COMPARE_SF_JUMP __ltsf2
kono
parents:
diff changeset
299 #endif /* L_ltsf2 */
kono
parents:
diff changeset
300
kono
parents:
diff changeset
301 #ifdef L_lesf2
kono
parents:
diff changeset
302 COMPARE_SF_JUMP lesf2
kono
parents:
diff changeset
303 #endif /* L_lesf2 */