Sync usage with man page.
[netbsd-mini2440.git] / lib / libc / pc532 / gen / modf.s
blob95a52ae7dda1714f961c7778379bb48152c3716b
1 /*
2 * Copyright (c) 1992 Helsinki University of Technology
3 * All Rights Reserved.
4 *
5 * Permission to use, copy, modify and distribute this software and its
6 * documentation is hereby granted, provided that both the copyright
7 * notice and this permission notice appear in all copies of the
8 * software, derivative works or modified versions, and any portions
9 * thereof, and that both notices appear in supporting documentation.
11 * HELSINKI UNIVERSITY OF TECHNOLOGY ALLOWS FREE USE OF THIS SOFTWARE IN
12 * ITS "AS IS" CONDITION. HELSINKI UNIVERSITY OF TECHNOLOGY DISCLAIMS ANY
13 * LIABILITY OF ANY KIND FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE
14 * USE OF THIS SOFTWARE.
17 * HISTORY
18 * 29-Apr-92 Tero Kivinen (kivinen) at Helsinki University of Technology
19 * Created.
21 * $Id: modf.s,v 1.1 1993/09/17 18:43:46 phil Exp $
25 * double modf (value, iptr)
26 * double value, *iptr;
28 * Modf returns the fractional part of "value",
29 * and stores the integer part indirectly through "iptr".
32 #include <machine/asm.h>
34 ENTRY(modf)
35 FRAME
36 movl 8(fp),f0 /* value */
37 movd 12(fp),r0 /* higher 32 bit of value */
38 lshd -20,r0 /* extract exponent */
39 andd 0x7ff,r0 /* 11 lower bits */
40 cmpd r0,1023+30 /* compare if it's int part can fit in int */
41 bgt modf_overflow /* nope else it's ok to truncld it to int*/
42 truncld f0,r0 /* get integer part */
43 movdl r0,f2 /* convert back to float */
44 movl f2,0(16(fp)) /* move integer part to *iptr */
45 subl f2,f0 /* return fract. part = value - *iptr */
46 EMARF
47 ret 0
48 modf_overflow:
49 subd 1023+20,r0 /* bias 1023, and upper part of
50 floating point mantissa part */
51 movqd -1,r2 /* generate mask to get fract. part */
52 cmpd r0,32 /* if value > 2^52 (20+32) then all int part */
53 bhi modf_all_ip
54 negd r0,r0 /* shift right */
55 lshd r0,r2 /* here */
56 comd r2,r2 /* get fractional part complement mask */
57 movd 8(fp),r1 /* get lower 32 bit of value */
58 andd r2,r1 /* mask fractional part off leave ip part */
59 movd r1,0(16(fp)) /* store ip part to *iptr */
60 movd 12(fp),4(16(fp)) /* store other half to *iptr */
61 subl 0(16(fp)),f0 /* return fract. part = value - *iptr */
62 EMARF
63 ret 0
64 modf_all_ip:
65 movl 8(fp),0(16(fp)) /* copy value to *iptr */
66 movdl 0,f0 /* return 0 for fract. part */
67 EMARF
68 ret 0