]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/compiler-rt/lib/builtins/hexagon/fastmath2_ldlib_asm.S
MFV r346450:
[FreeBSD/FreeBSD.git] / contrib / compiler-rt / lib / builtins / hexagon / fastmath2_ldlib_asm.S
1 //===----------------------Hexagon builtin routine ------------------------===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is dual licensed under the MIT and the University of Illinois Open
6 // Source Licenses. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 /* ==================================================================== *
10
11 fast2_QLDOUBLE fast2_ldadd(fast2_QLDOUBLE a,fast2_QLDOUBLE b) {
12       fast2_QLDOUBLE c;
13       lint manta = a & MANTMASK;
14       int  expa  = Q6_R_sxth_R(a) ;
15       lint mantb = b & MANTMASK;
16       int  expb  = Q6_R_sxth_R(b) ;
17       int  exp, expdiff, j, k, hi, lo, cn;
18       lint mant;
19
20         expdiff = (int) Q6_P_vabsdiffh_PP(a, b);
21         expdiff = Q6_R_sxth_R(expdiff) ;
22         if (expdiff > 63) { expdiff = 62;}
23         if (expa > expb) {
24           exp = expa + 1;
25           expa = 1;
26           expb = expdiff + 1;
27         } else {
28           exp = expb + 1;
29           expb = 1;
30           expa = expdiff + 1;
31         }
32         mant = (manta>>expa) + (mantb>>expb);
33
34         hi = (int) (mant>>32);
35         lo = (int) (mant);
36
37         k =  Q6_R_normamt_R(hi);
38         if(hi == 0 || hi == -1) k = 31+Q6_R_normamt_R(lo);
39
40         mant = (mant << k);
41         cn  = (mant == 0x8000000000000000LL);
42         exp = exp - k + cn;
43
44         if (mant ==  0 || mant == -1)  exp = 0x8001;
45         c = (mant & MANTMASK) | (((lint) exp) & EXP_MASK);
46       return(c);
47  }
48  * ==================================================================== */
49         .text
50         .global fast2_ldadd_asm
51         .type fast2_ldadd_asm, @function
52 fast2_ldadd_asm:
53 #define manta      R1:0
54 #define lmanta     R1:0
55 #define mantb      R3:2
56 #define lmantb     R3:2
57 #define expa       R4
58 #define expb       R5
59 #define expd       R6
60 #define exp        R8
61 #define c63        R9
62 #define lmant      R1:0
63 #define k          R4
64 #define ce         P0
65 #define zero       R3:2
66         .falign
67       {
68         expa = memw(r29+#8)
69         expb = memw(r29+#24)
70         r7 = r0
71       }
72       {
73         expd = sub(expa, expb):sat
74         ce = CMP.GT(expa, expb);
75         if ( ce.new) exp = add(expa, #1)
76         if (!ce.new) exp = add(expb, #1)
77       } {
78         expd = abs(expd):sat
79         if ( ce) expa = #1
80         if (!ce) expb = #1
81         c63 = #62
82       } {
83         expd = MIN(expd, c63)
84         manta = memd(r29+#0)
85         mantb = memd(r29+#16)
86       } {
87         if (!ce) expa = add(expd, #1)
88         if ( ce) expb = add(expd, #1)
89       } {
90         lmanta = ASR(lmanta, expa)
91         lmantb = ASR(lmantb, expb)
92       } {
93         lmant = add(lmanta, lmantb)
94         zero = #0
95       } {
96         k  = clb(lmant)
97         c63.L =#0x0001
98       } {
99         exp -= add(k, #-1)  //exp =  exp - (k-1)
100         k = add(k, #-1)
101         p0 = cmp.gt(k, #58)
102         c63.H =#0x8000
103       } {
104         if(!p0)memw(r7+#8) = exp
105         lmant = ASL(lmant, k)
106         if(p0) jump .Ldenorma
107       } {
108         memd(r7+#0) = lmant
109         jumpr  r31
110       }
111 .Ldenorma:
112         memd(r7+#0) = zero
113       {
114         memw(r7+#8) = c63
115         jumpr  r31
116       }
117 /* =================================================================== *
118  fast2_QLDOUBLE fast2_ldsub(fast2_QLDOUBLE a,fast2_QLDOUBLE b) {
119       fast2_QLDOUBLE c;
120       lint manta = a & MANTMASK;
121       int  expa  = Q6_R_sxth_R(a) ;
122       lint mantb = b & MANTMASK;
123       int  expb  = Q6_R_sxth_R(b) ;
124       int  exp, expdiff, j, k;
125       lint mant;
126
127         expdiff = (int) Q6_P_vabsdiffh_PP(a, b);
128         expdiff = Q6_R_sxth_R(expdiff) ;
129         if (expdiff > 63) { expdiff = 62;}
130         if (expa > expb) {
131           exp = expa + 1;
132           expa = 1;
133           expb = expdiff + 1;
134         } else {
135           exp = expb + 1;
136           expb = 1;
137           expa = expdiff + 1;
138         }
139         mant = (manta>>expa) - (mantb>>expb);
140         k =  Q6_R_clb_P(mant)-1;
141         mant = (mant << k);
142         exp = exp - k;
143         if (mant ==  0 || mant == -1)  exp = 0x8001;
144         c = (mant & MANTMASK) | (((lint) exp) & EXP_MASK);
145       return(c);
146  }
147  * ==================================================================== */
148         .text
149         .global fast2_ldsub_asm
150         .type fast2_ldsub_asm, @function
151 fast2_ldsub_asm:
152 #define manta      R1:0
153 #define lmanta     R1:0
154 #define mantb      R3:2
155 #define lmantb     R3:2
156 #define expa       R4
157 #define expb       R5
158 #define expd       R6
159 #define exp        R8
160 #define c63        R9
161 #define lmant      R1:0
162 #define k          R4
163 #define ce         P0
164 #define zero       R3:2
165         .falign
166       {
167         expa = memw(r29+#8)
168         expb = memw(r29+#24)
169         r7 = r0
170       }
171       {
172         expd = sub(expa, expb):sat
173         ce = CMP.GT(expa, expb);
174         if ( ce.new) exp = add(expa, #1)
175         if (!ce.new) exp = add(expb, #1)
176       } {
177         expd = abs(expd):sat
178         if ( ce) expa = #1
179         if (!ce) expb = #1
180         c63 = #62
181       } {
182         expd = min(expd, c63)
183         manta = memd(r29+#0)
184         mantb = memd(r29+#16)
185       } {
186         if (!ce) expa = add(expd, #1)
187         if ( ce) expb = add(expd, #1)
188       } {
189         lmanta = ASR(lmanta, expa)
190         lmantb = ASR(lmantb, expb)
191       } {
192         lmant = sub(lmanta, lmantb)
193         zero = #0
194       } {
195         k  = clb(lmant)
196         c63.L =#0x0001
197       } {
198         exp -= add(k, #-1)  //exp =  exp - (k+1)
199         k = add(k, #-1)
200         p0 = cmp.gt(k, #58)
201         c63.H =#0x8000
202       } {
203         if(!p0)memw(r7+#8) = exp
204         lmant = asl(lmant, k)
205         if(p0) jump .Ldenorma_s
206       } {
207         memd(r7+#0) = lmant
208         jumpr  r31
209       }
210 .Ldenorma_s:
211         memd(r7+#0) = zero
212       {
213         memw(r7+#8) = c63
214         jumpr  r31
215       }
216
217 /* ==================================================================== *
218  fast2_QLDOUBLE fast2_ldmpy(fast2_QLDOUBLE a,fast2_QLDOUBLE b) {
219         fast2_QLDOUBLE c;
220         lint manta = a & MANTMASK;
221         int  expa  = Q6_R_sxth_R(a) ;
222         lint mantb = b & MANTMASK;
223         int  expb  = Q6_R_sxth_R(b) ;
224         int exp, k;
225         lint mant;
226         int          hia, hib, hi, lo;
227         unsigned int loa, lob;
228
229         hia = (int)(a >> 32);
230         loa = Q6_R_extractu_RII((int)manta, 31, 1);
231         hib = (int)(b >> 32);
232         lob = Q6_R_extractu_RII((int)mantb, 31, 1);
233
234         mant = Q6_P_mpy_RR(hia, lob);
235         mant = Q6_P_mpyacc_RR(mant,hib, loa);
236         mant = (mant >> 30) + (Q6_P_mpy_RR(hia, hib)<<1);
237
238         hi = (int) (mant>>32);
239
240         k =  Q6_R_normamt_R(hi);
241         mant = mant << k;
242         exp = expa + expb - k;
243         if (mant ==  0 || mant == -1)  exp = 0x8001;
244         c = (mant & MANTMASK) | (((lint) exp) & EXP_MASK);
245         return(c);
246  }
247  * ==================================================================== */
248         .text
249         .global fast2_ldmpy_asm
250         .type fast2_ldmpy_asm, @function
251 fast2_ldmpy_asm:
252
253 #define mantxl_    R9
254 #define mantxl     R14
255 #define mantxh     R15
256 #define mantx      R15:14
257 #define mantbl     R2
258 #define mantbl_    R8
259 #define mantbh     R3
260 #define mantb      R3:2
261 #define expa       R4
262 #define expb       R5
263 #define c8001      R8
264 #define mantd      R7:6
265 #define lmantc     R11:10
266 #define kp         R9
267 #define min        R13:12
268 #define minh       R13
269 #define max        R13:12
270 #define maxh       R13
271 #define ret        R0
272
273         .falign
274       {
275         mantx = memd(r29+#0)
276         mantb = memd(r29+#16)
277         min = #0
278       }
279       {
280         mantbl_= extractu(mantbl, #31, #1)
281         mantxl_= extractu(mantxl, #31, #1)
282         minh.H = #0x8000
283       }
284       {
285         lmantc = mpy(mantxh, mantbh)
286         mantd = mpy(mantxh, mantbl_)
287         expa = memw(r29+#8)
288         expb = memw(r29+#24)
289       }
290       {
291         lmantc = add(lmantc, lmantc)
292         mantd += mpy(mantbh, mantxl_)
293       }
294       {
295         mantd = asr(mantd, #30)
296         c8001.L =  #0x0001
297         p1 = cmp.eq(mantx, mantb)
298       }
299       {
300         mantd = add(mantd, lmantc)
301         expa= add(expa, expb)
302         p2 = cmp.eq(mantb, min)
303       }
304       {
305         kp  = clb(mantd)
306         c8001.H =  #0x8000
307         p1 = and(p1, p2)
308       }
309       {
310         expa-= add(kp, #-1)
311         kp = add(kp, #-1)
312         if(p1) jump .Lsat
313       }
314       {
315         mantd = asl(mantd, kp)
316         memw(ret+#8) = expa
317         p0 = cmp.gt(kp, #58)
318         if(p0.new) jump:NT .Ldenorm   //rarely happens
319       }
320       {
321         memd(ret+#0) = mantd
322         jumpr  r31
323       }
324 .Lsat:
325       {
326         max = #0
327         expa+= add(kp, #1)
328       }
329       {
330         maxh.H = #0x4000
331         memw(ret+#8) = expa
332       }
333       {
334         memd(ret+#0) = max
335         jumpr  r31
336       }
337 .Ldenorm:
338       {
339         memw(ret+#8) = c8001
340         mantx = #0
341       }
342       {
343         memd(ret+#0) = mantx
344         jumpr  r31
345       }