OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-old/] [gcc-4.2.2/] [gcc/] [config/] [mcore/] [lib1.asm] - Blame information for rev 816

Details | Compare with Previous | View Log

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

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.