~ubuntu-branches/ubuntu/utopic/eglibc/utopic

« back to all changes in this revision

Viewing changes to ports/sysdeps/ia64/fpu/libm_scalblnf.S

  • Committer: Package Import Robot
  • Author(s): Adam Conrad
  • Date: 2012-10-26 05:14:58 UTC
  • mfrom: (1.5.1) (4.4.22 experimental)
  • Revision ID: package-import@ubuntu.com-20121026051458-oryotr4i03ob5pab
Tags: 2.16-0ubuntu1
* Merge with unreleased 2.16 in Debian experimental, remaining changes:
  - Drop the Breaks line from libc6, which refers to a Debian transition
  - Remove the libc6 recommends on libc6-i686, which we don't build
  - Enable libc6{,-dev}-armel on armhf and libc6{-dev}-armhf on armel
  - Ship update-locale and validlocale in /usr/sbin in libc-bin
  - Don't build locales or locales-all in Ubuntu, we rely on langpacks
  - Heavily mangle the way we do service restarting on major upgrades
  - Use different MIN_KERNEL_SUPPORTED versions than Debian, due to
    buildd needs.  This should be universally bumped to 3.2.0 once all
    our buildds (including the PPA guests) are running precise kernels
  - Build i386 variants as -march=i686, build amd64 with -O3, and build
    ppc64 variants (both 64-bit and 32-bit) with -O3 -fno-tree-vectorize
  - Re-enable unsubmitted-ldconfig-cache-abi.diff and rebuild the cache
    on upgrades from previous versions that used a different constant
  - debian/patches/any/local-CVE-2012-3406.diff: switch to malloc when
    array grows too large to handle via alloca extension (CVE-2012-3406)
  - Build generic i386/i686 flavour with -mno-tls-direct-seg-refs
* Changes added/dropped with this merge while reducing our delta:
  - Stop building glibc docs from the eglibc source, and instead make
    the glibc-docs stub have a hard dependency on glibc-doc-reference
  - Remove outdated conflicts against ancient versions of ia32-libs
  - Drop the tzdata dependency from libc6, it's in required and minimal
  - Use gcc-4.7/g++-4.7 by default on all our supported architectures
  - Save our historical changelog as changelog.ubuntu in the source
  - Drop nscd's libaudit build-dep for now, as libaudit is in universe
  - Drop the unnecessary Breaks from libc6 to locales and locales-all
  - Ship xen's ld.so.conf.d snippet as /etc/ld.so.conf.d/libc6-xen.conf
* Disable hard failures on the test suite for the first upload to raring

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
.file "libm_scalblnf.s"
 
2
 
 
3
 
 
4
// Copyright (c) 2001 - 2003, Intel Corporation
 
5
// All rights reserved.
 
6
//
 
7
// Contributed 2001 by the Intel Numerics Group, Intel Corporation
 
8
//
 
9
// Redistribution and use in source and binary forms, with or without
 
10
// modification, are permitted provided that the following conditions are
 
11
// met:
 
12
//
 
13
// * Redistributions of source code must retain the above copyright
 
14
// notice, this list of conditions and the following disclaimer.
 
15
//
 
16
// * Redistributions in binary form must reproduce the above copyright
 
17
// notice, this list of conditions and the following disclaimer in the
 
18
// documentation and/or other materials provided with the distribution.
 
19
//
 
20
// * The name of Intel Corporation may not be used to endorse or promote
 
21
// products derived from this software without specific prior written
 
22
// permission.
 
23
 
 
24
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
 
25
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
 
26
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
 
27
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL INTEL OR ITS
 
28
// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
 
29
// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
 
30
// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
 
31
// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
 
32
// OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY OR TORT (INCLUDING
 
33
// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
 
34
// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 
35
//
 
36
// Intel Corporation is the author of this code, and requests that all
 
37
// problem reports or change requests be submitted to it directly at
 
38
// http://www.intel.com/software/products/opensource/libraries/num.htm.
 
39
//
 
40
// History
 
41
//==============================================================
 
42
// 08/03/01 Initial version
 
43
// 08/23/01 Corrected error tag number
 
44
// 02/06/02 Corrected to handle 32- or 64-bit integers
 
45
// 05/20/02 Cleaned up namespace and sf0 syntax
 
46
// 02/10/03 Reordered header: .section, .global, .proc, .align
 
47
// 08/25/03 Improved performance
 
48
//
 
49
// API
 
50
//==============================================================
 
51
// float __libm_scalblnf  (float x, long int n, int long_int_type)
 
52
// input  floating point f8 and long int n (r33)
 
53
// input  long_int_type = 0 if long int defined as 32 bits, = 1 if 64 bits
 
54
// output floating point f8
 
55
//
 
56
// Returns x* 2**n using an fma and detects overflow
 
57
// and underflow.
 
58
//
 
59
//
 
60
// Strategy:
 
61
//  Compute biased exponent of result exp_Result = N + exp_X
 
62
//  Break into ranges:
 
63
//   exp_Result > 0x1007e                 -> Certain overflow
 
64
//   exp_Result = 0x1007e                 -> Possible overflow
 
65
//   0x0ff81 <= exp_Result < 0x1007e      -> No over/underflow (main path)
 
66
//   0x0ff81 - 23 <= exp_Result < 0x0ff81 -> Possible underflow
 
67
//   exp_Result < 0x0ff81 - 23            -> Certain underflow
 
68
 
 
69
FR_Big         = f6
 
70
FR_NBig        = f7
 
71
FR_Floating_X  = f8
 
72
FR_Result      = f8
 
73
FR_Result2     = f9
 
74
FR_Result3     = f10
 
75
FR_Norm_X      = f11
 
76
FR_Two_N       = f12
 
77
 
 
78
GR_neg_ov_limit= r14
 
79
GR_N_Biased    = r15
 
80
GR_Big         = r16
 
81
GR_NBig        = r17
 
82
GR_exp_Result  = r18
 
83
GR_pos_ov_limit= r19
 
84
GR_Bias        = r20
 
85
GR_N_as_int    = r21
 
86
GR_signexp_X   = r22
 
87
GR_exp_X       = r23
 
88
GR_exp_mask    = r24
 
89
GR_max_exp     = r25
 
90
GR_min_exp     = r26
 
91
GR_min_den_exp = r27
 
92
 
 
93
GR_SAVE_B0          = r32
 
94
GR_SAVE_GP          = r33
 
95
GR_SAVE_PFS         = r34
 
96
GR_Parameter_X      = r35
 
97
GR_Parameter_Y      = r36
 
98
GR_Parameter_RESULT = r37
 
99
GR_Tag              = r38
 
100
 
 
101
.section .text
 
102
GLOBAL_LIBM_ENTRY(__libm_scalblnf)
 
103
 
 
104
//
 
105
//   Is x NAN, INF, ZERO, +-?
 
106
//   Build the exponent Bias
 
107
//
 
108
{    .mfi
 
109
     getf.exp      GR_signexp_X = FR_Floating_X // Get signexp of x
 
110
     fclass.m      p6,p0 = FR_Floating_X, 0xe7  // @snan | @qnan | @inf | @zero
 
111
     mov           GR_Bias = 0x0ffff
 
112
}
 
113
//
 
114
//   Normalize x
 
115
//   Is long integer type 32 bits?
 
116
//
 
117
{    .mfi
 
118
     mov           GR_Big = 35000      // If N this big then certain overflow
 
119
     fnorm.s1      FR_Norm_X = FR_Floating_X
 
120
     cmp.eq        p8,p9 = r34,r0
 
121
}
 
122
;;
 
123
 
 
124
//   Sign extend N if long int is 32 bits
 
125
{    .mfi
 
126
(p9) mov           GR_N_as_int = r33     // Copy N if long int is 64 bits
 
127
     fclass.m      p9,p0 = FR_Floating_X, 0x0b // Test for x=unorm
 
128
(p8) sxt4          GR_N_as_int = r33     // Sign extend N if long int is 32 bits
 
129
}
 
130
{ .mfi
 
131
     mov           GR_NBig = -35000    // If N this small then certain underflow
 
132
     nop.f         0
 
133
     mov           GR_max_exp = 0x1007e      // Exponent of maximum float
 
134
}
 
135
;;
 
136
 
 
137
//   Create biased exponent for 2**N
 
138
{    .mfi
 
139
     add           GR_N_Biased = GR_Bias,GR_N_as_int
 
140
     nop.f         0
 
141
     cmp.ge        p7, p0 = GR_N_as_int, GR_Big  // Certain overflow?
 
142
}
 
143
{    .mib
 
144
     cmp.le        p8, p0 = GR_N_as_int, GR_NBig // Certain underflow?
 
145
     mov           GR_min_exp = 0x0ff81      // Exponent of minimum float
 
146
(p9) br.cond.spnt  SCALBNF_UNORM              // Branch if x=unorm
 
147
}
 
148
;;
 
149
 
 
150
SCALBNF_COMMON:
 
151
// Main path continues.  Also return here from x=unorm path.
 
152
//   Create 2**N
 
153
.pred.rel "mutex",p7,p8
 
154
{    .mfi
 
155
     setf.exp      FR_Two_N = GR_N_Biased
 
156
     nop.f         0
 
157
(p7) mov           GR_N_as_int = GR_Big      // Limit max N
 
158
}
 
159
{    .mfi
 
160
(p8) mov           GR_N_as_int = GR_NBig     // Limit min N
 
161
     nop.f         0
 
162
(p8) cmp.eq        p7,p0 = r0,r0             // Set p7 if |N| big
 
163
}
 
164
;;
 
165
 
 
166
//
 
167
//   Create biased exponent for 2**N for N big
 
168
//   Is N zero?
 
169
//
 
170
{    .mfi
 
171
(p7) add           GR_N_Biased = GR_Bias,GR_N_as_int
 
172
     nop.f         0
 
173
     cmp.eq.or     p6,p0 = r33,r0
 
174
}
 
175
{    .mfi
 
176
     mov           GR_pos_ov_limit = 0x1007f // Exponent for positive overflow
 
177
     nop.f         0
 
178
     mov           GR_exp_mask = 0x1ffff     // Exponent mask
 
179
}
 
180
;;
 
181
 
 
182
//
 
183
//   Create 2**N for N big
 
184
//   Return x when N = 0 or X = Nan, Inf, Zero
 
185
//
 
186
{    .mfi
 
187
(p7) setf.exp      FR_Two_N = GR_N_Biased
 
188
     nop.f         0
 
189
     mov           GR_min_den_exp = 0x0ff81 - 23 // Exponent of min denorm float
 
190
}
 
191
{    .mfb
 
192
     and           GR_exp_X = GR_exp_mask, GR_signexp_X
 
193
(p6) fma.s.s0      FR_Result = FR_Floating_X, f1, f0
 
194
(p6) br.ret.spnt   b0
 
195
}
 
196
;;
 
197
 
 
198
//
 
199
//   Raise Denormal operand flag with compare
 
200
//   Compute biased result exponent
 
201
//
 
202
{    .mfi
 
203
     add           GR_exp_Result = GR_exp_X, GR_N_as_int
 
204
     fcmp.ge.s0    p0,p11 = FR_Floating_X,f0
 
205
     mov           GR_neg_ov_limit = 0x3007f // Exponent for negative overflow
 
206
}
 
207
;;
 
208
 
 
209
//
 
210
//   Do final operation
 
211
//
 
212
{    .mfi
 
213
     cmp.lt        p7,p6 = GR_exp_Result, GR_max_exp  // Test no overflow
 
214
     fma.s.s0      FR_Result = FR_Two_N,FR_Norm_X,f0
 
215
     cmp.lt        p9,p0 = GR_exp_Result, GR_min_den_exp // Test sure underflow
 
216
}
 
217
{    .mfb
 
218
     nop.m         0
 
219
     nop.f         0
 
220
(p9) br.cond.spnt  SCALBNF_UNDERFLOW           // Branch if certain underflow
 
221
}
 
222
;;
 
223
 
 
224
{    .mib
 
225
(p6) cmp.gt.unc    p6,p8 = GR_exp_Result, GR_max_exp  // Test sure overflow
 
226
(p7) cmp.ge.unc    p7,p9 = GR_exp_Result, GR_min_exp  // Test no over/underflow
 
227
(p7) br.ret.sptk   b0                         // Return from main path
 
228
}
 
229
;;
 
230
 
 
231
{    .bbb
 
232
(p6) br.cond.spnt  SCALBNF_OVERFLOW            // Branch if certain overflow
 
233
(p8) br.cond.spnt  SCALBNF_POSSIBLE_OVERFLOW   // Branch if possible overflow
 
234
(p9) br.cond.spnt  SCALBNF_POSSIBLE_UNDERFLOW  // Branch if possible underflow
 
235
}
 
236
;;
 
237
 
 
238
// Here if possible underflow.
 
239
// Resulting exponent: 0x0ff81-23 <= exp_Result < 0x0ff81
 
240
SCALBNF_POSSIBLE_UNDERFLOW:
 
241
//
 
242
// Here if possible overflow.
 
243
// Resulting exponent: 0x1007e = exp_Result
 
244
SCALBNF_POSSIBLE_OVERFLOW:
 
245
 
 
246
//   Set up necessary status fields
 
247
//
 
248
//   S0 user supplied status
 
249
//   S2 user supplied status + WRE + TD  (Overflows)
 
250
//   S3 user supplied status + FZ + TD   (Underflows)
 
251
//
 
252
{    .mfi
 
253
     nop.m         0
 
254
     fsetc.s3      0x7F,0x41
 
255
     nop.i         0
 
256
}
 
257
{    .mfi
 
258
     nop.m         0
 
259
     fsetc.s2      0x7F,0x42
 
260
     nop.i         0
 
261
}
 
262
;;
 
263
 
 
264
//
 
265
//   Do final operation with s2 and s3
 
266
//
 
267
{    .mfi
 
268
     setf.exp      FR_NBig = GR_neg_ov_limit
 
269
     fma.s.s3      FR_Result3 = FR_Two_N,FR_Norm_X,f0
 
270
     nop.i         0
 
271
}
 
272
{    .mfi
 
273
     setf.exp      FR_Big = GR_pos_ov_limit
 
274
     fma.s.s2      FR_Result2 = FR_Two_N,FR_Norm_X,f0
 
275
     nop.i         0
 
276
}
 
277
;;
 
278
 
 
279
//   Check for overflow or underflow.
 
280
//   Restore s3
 
281
//   Restore s2
 
282
//
 
283
{    .mfi
 
284
     nop.m         0
 
285
     fsetc.s3      0x7F,0x40
 
286
     nop.i         0
 
287
}
 
288
{    .mfi
 
289
     nop.m         0
 
290
     fsetc.s2      0x7F,0x40
 
291
     nop.i         0
 
292
}
 
293
;;
 
294
 
 
295
//
 
296
//   Is the result zero?
 
297
//
 
298
{    .mfi
 
299
     nop.m         0
 
300
     fclass.m      p6, p0 =  FR_Result3, 0x007
 
301
     nop.i         0
 
302
}
 
303
{    .mfi
 
304
     nop.m         0
 
305
     fcmp.ge.s1    p7, p8 = FR_Result2 , FR_Big
 
306
     nop.i         0
 
307
}
 
308
;;
 
309
 
 
310
//
 
311
//   Detect masked underflow - Tiny + Inexact Only
 
312
//
 
313
{    .mfi
 
314
     nop.m         0
 
315
(p6) fcmp.neq.unc.s1 p6, p0 = FR_Result , FR_Result2
 
316
     nop.i         0
 
317
}
 
318
;;
 
319
 
 
320
//
 
321
//   Is result bigger the allowed range?
 
322
//   Branch out for underflow
 
323
//
 
324
{    .mfb
 
325
     nop.m          0
 
326
(p8) fcmp.le.unc.s1 p9, p10 = FR_Result2 , FR_NBig
 
327
(p6) br.cond.spnt   SCALBNF_UNDERFLOW
 
328
}
 
329
;;
 
330
 
 
331
//
 
332
//   Branch out for overflow
 
333
//
 
334
{ .bbb
 
335
(p7) br.cond.spnt   SCALBNF_OVERFLOW
 
336
(p9) br.cond.spnt   SCALBNF_OVERFLOW
 
337
     br.ret.sptk    b0             //   Return from main path.
 
338
}
 
339
;;
 
340
 
 
341
// Here if result overflows
 
342
SCALBNF_OVERFLOW:
 
343
{ .mib
 
344
     alloc         r32=ar.pfs,3,0,4,0
 
345
     addl          GR_Tag = 205, r0    // Set error tag for overflow
 
346
     br.cond.sptk  __libm_error_region // Call error support for overflow
 
347
}
 
348
;;
 
349
 
 
350
// Here if result underflows
 
351
SCALBNF_UNDERFLOW:
 
352
{ .mib
 
353
     alloc         r32=ar.pfs,3,0,4,0
 
354
     addl          GR_Tag = 206, r0    // Set error tag for underflow
 
355
     br.cond.sptk  __libm_error_region // Call error support for underflow
 
356
}
 
357
;;
 
358
 
 
359
// Here if x=unorm
 
360
SCALBNF_UNORM:
 
361
{ .mib
 
362
     getf.exp      GR_signexp_X = FR_Norm_X // Get signexp of normalized x
 
363
     nop.i         0
 
364
     br.cond.sptk  SCALBNF_COMMON            // Return to main path
 
365
}
 
366
;;
 
367
 
 
368
 
 
369
GLOBAL_LIBM_END(__libm_scalblnf)
 
370
LOCAL_LIBM_ENTRY(__libm_error_region)
 
371
 
 
372
//
 
373
// Get stack address of N
 
374
//
 
375
.prologue
 
376
{ .mfi
 
377
    add   GR_Parameter_Y=-32,sp
 
378
    nop.f 0
 
379
.save   ar.pfs,GR_SAVE_PFS
 
380
    mov  GR_SAVE_PFS=ar.pfs
 
381
}
 
382
//
 
383
// Adjust sp
 
384
//
 
385
{ .mfi
 
386
.fframe 64
 
387
   add sp=-64,sp
 
388
   nop.f 0
 
389
   mov GR_SAVE_GP=gp
 
390
};;
 
391
 
 
392
//
 
393
//  Store N on stack in correct position
 
394
//  Locate the address of x on stack
 
395
//
 
396
{ .mmi
 
397
   st8 [GR_Parameter_Y] =  GR_N_as_int,16
 
398
   add GR_Parameter_X = 16,sp
 
399
.save   b0, GR_SAVE_B0
 
400
   mov GR_SAVE_B0=b0
 
401
};;
 
402
 
 
403
//
 
404
// Store x on the stack.
 
405
// Get address for result on stack.
 
406
//
 
407
.body
 
408
{ .mib
 
409
   stfs [GR_Parameter_X] = FR_Norm_X
 
410
   add   GR_Parameter_RESULT = 0,GR_Parameter_Y
 
411
   nop.b 0
 
412
}
 
413
{ .mib
 
414
   stfs [GR_Parameter_Y] = FR_Result
 
415
   add   GR_Parameter_Y = -16,GR_Parameter_Y
 
416
   br.call.sptk b0=__libm_error_support#
 
417
};;
 
418
 
 
419
//
 
420
//  Get location of result on stack
 
421
//
 
422
{ .mmi
 
423
   add   GR_Parameter_RESULT = 48,sp
 
424
   nop.m 0
 
425
   nop.i 0
 
426
};;
 
427
 
 
428
//
 
429
//  Get the new result
 
430
//
 
431
{ .mmi
 
432
   ldfs  FR_Result = [GR_Parameter_RESULT]
 
433
.restore sp
 
434
   add   sp = 64,sp
 
435
   mov   b0 = GR_SAVE_B0
 
436
};;
 
437
 
 
438
//
 
439
//  Restore gp, ar.pfs and return
 
440
//
 
441
{ .mib
 
442
   mov   gp = GR_SAVE_GP
 
443
   mov   ar.pfs = GR_SAVE_PFS
 
444
   br.ret.sptk     b0
 
445
};;
 
446
 
 
447
LOCAL_LIBM_END(__libm_error_region)
 
448
 
 
449
.type   __libm_error_support#,@function
 
450
.global __libm_error_support#