Skip to content

Instantly share code, notes, and snippets.

@olajep
Last active August 29, 2015 14:22
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save olajep/102e1b0a2ce3d38b834c to your computer and use it in GitHub Desktop.
Save olajep/102e1b0a2ce3d38b834c to your computer and use it in GitHub Desktop.
clang-divsf3-e-gcc-Os
divsf3.o: file format elf32-epiphany
Disassembly of section .text:
00000000 <___divsf3>:
#include "fp_lib.h"
ARM_EABI_FNALIAS(fdiv, divsf3)
COMPILER_RT_ABI fp_t
__divsf3(fp_t a, fp_t b) {
0: 977c 0700 strd r4,[sp],-0x6
4: 60e2 mov r3,r0
6: 55fc 2400 strd r10,[sp,+0x3]
const unsigned int aExponent = toRep(a) >> significandBits & maxExponent;
a: 62ef 2006 lsr fp,r0,0x17
const unsigned int bExponent = toRep(b) >> significandBits & maxExponent;
e: 46ef 2006 lsr r10,r1,0x17
ARM_EABI_FNALIAS(fdiv, divsf3)
COMPILER_RT_ABI fp_t
__divsf3(fp_t a, fp_t b) {
const unsigned int aExponent = toRep(a) >> significandBits & maxExponent;
12: 1fe3 mov r0,0xff
14: 6c5f 240a and fp,fp,r0
#include "fp_lib.h"
ARM_EABI_FNALIAS(fdiv, divsf3)
COMPILER_RT_ABI fp_t
__divsf3(fp_t a, fp_t b) {
18: 167c 2400 strd r8,[sp,+0x4]
const unsigned int aExponent = toRep(a) >> significandBits & maxExponent;
const unsigned int bExponent = toRep(b) >> significandBits & maxExponent;
1c: 485f 240a and r10,r10,r0
const rep_t quotientSign = (toRep(a) ^ toRep(b)) & signBit;
rep_t aSignificand = toRep(a) & significandMask;
20: 1feb 2ff2 mov r8,0xffff
COMPILER_RT_ABI fp_t
__divsf3(fp_t a, fp_t b) {
const unsigned int aExponent = toRep(a) >> significandBits & maxExponent;
const unsigned int bExponent = toRep(b) >> significandBits & maxExponent;
const rep_t quotientSign = (toRep(a) ^ toRep(b)) & signBit;
24: 000b 0002 mov r0,0x0
28: 000b 1802 movt r0,0x8000
rep_t aSignificand = toRep(a) & significandMask;
2c: 0feb 3002 movt r8,0x7f
#include "fp_lib.h"
ARM_EABI_FNALIAS(fdiv, divsf3)
COMPILER_RT_ABI fp_t
__divsf3(fp_t a, fp_t b) {
30: d6fc 0400 strd r6,[sp,+0x5]
const unsigned int aExponent = toRep(a) >> significandBits & maxExponent;
const unsigned int bExponent = toRep(b) >> significandBits & maxExponent;
const rep_t quotientSign = (toRep(a) ^ toRep(b)) & signBit;
34: e58a eor r7,r1,r3
36: fc5a and r7,r7,r0
rep_t aSignificand = toRep(a) & significandMask;
38: 21df 240a and r9,r8,r3
rep_t bSignificand = toRep(b) & significandMask;
int scale = 0;
// Detect if a or b is zero, denormal, infinity, or NaN.
if (aExponent-1U >= maxExponent-1U || bExponent-1U >= maxExponent-1U) {
3c: 0f9b 04ff add r0,fp,-1
const unsigned int aExponent = toRep(a) >> significandBits & maxExponent;
const unsigned int bExponent = toRep(b) >> significandBits & maxExponent;
const rep_t quotientSign = (toRep(a) ^ toRep(b)) & signBit;
rep_t aSignificand = toRep(a) & significandMask;
rep_t bSignificand = toRep(b) & significandMask;
40: 00df 240a and r8,r8,r1
#include "fp_lib.h"
ARM_EABI_FNALIAS(fdiv, divsf3)
COMPILER_RT_ABI fp_t
__divsf3(fp_t a, fp_t b) {
44: d57c 2400 strd lr,[sp,+0x2]
48: 15dc 8400 str r32,[sp,+0x3]
rep_t aSignificand = toRep(a) & significandMask;
rep_t bSignificand = toRep(b) & significandMask;
int scale = 0;
// Detect if a or b is zero, denormal, infinity, or NaN.
if (aExponent-1U >= maxExponent-1U || bExponent-1U >= maxExponent-1U) {
4c: 42bb 001f sub r2,r0,253
50: 0620 bgtu 5c <___divsf3+0x5c>
52: 0b9b 04ff add r0,r10,-1
56: 82bb 201f sub r12,r0,253
5a: 6f40 blteu 138 <___divsf3+0x138>
const rep_t aAbs = toRep(a) & absMask;
5c: dfeb 0ff2 mov r6,0xffff
60: dfeb 17f2 movt r6,0x7fff
const rep_t bAbs = toRep(b) & absMask;
// NaN / anything = qNaN
if (aAbs > infRep) return fromRep(toRep(a) | quietBit);
64: 800b 2002 mov r12,0x0
int scale = 0;
// Detect if a or b is zero, denormal, infinity, or NaN.
if (aExponent-1U >= maxExponent-1U || bExponent-1U >= maxExponent-1U) {
const rep_t aAbs = toRep(a) & absMask;
68: 59da and r2,r6,r3
const rep_t bAbs = toRep(b) & absMask;
// NaN / anything = qNaN
if (aAbs > infRep) return fromRep(toRep(a) | quietBit);
6a: 900b 37f2 movt r12,0x7f80
6e: 0a3f 008a sub r0,r2,r12
72: 0840 blteu 82 <___divsf3+0x82>
return rep.i;
}
static inline fp_t fromRep(rep_t x) {
const union { fp_t f; rep_t i; } rep = {.i = x};
return rep.f;
74: 000b 0002 mov r0,0x0
78: 080b 1002 movt r0,0x40
7c: 01fa orr r0,r0,r3
7e: 3fe8 0001 b 2fc <___divsf3+0x2fc>
// Detect if a or b is zero, denormal, infinity, or NaN.
if (aExponent-1U >= maxExponent-1U || bExponent-1U >= maxExponent-1U) {
const rep_t aAbs = toRep(a) & absMask;
const rep_t bAbs = toRep(b) & absMask;
82: d8da and r6,r6,r1
// NaN / anything = qNaN
if (aAbs > infRep) return fromRep(toRep(a) | quietBit);
// anything / NaN = qNaN
if (bAbs > infRep) return fromRep(toRep(b) | quietBit);
84: 7a3f 008a sub r3,r6,r12
88: 0840 blteu 98 <___divsf3+0x98>
8a: 000b 0002 mov r0,0x0
8e: 080b 1002 movt r0,0x40
92: 00fa orr r0,r0,r1
94: 34e8 0001 b 2fc <___divsf3+0x2fc>
if (aAbs == infRep) {
98: 0a3f 008a sub r0,r2,r12
9c: 0710 bne aa <___divsf3+0xaa>
// infinity / infinity = NaN
if (bAbs == infRep) return fromRep(qnanRep);
9e: 393a sub r1,r6,r2
a0: 2a08 0001 beq 2f4 <___divsf3+0x2f4>
a4: 1d7a orr r0,r7,r2
// infinity / anything else = +/- infinity
else return fromRep(aAbs | quotientSign);
a6: 2be8 0001 b 2fc <___divsf3+0x2fc>
}
// anything else / infinity = +/- 0
if (bAbs == infRep) return fromRep(quotientSign);
aa: 7a3f 008a sub r3,r6,r12
ae: 0410 bne b6 <___divsf3+0xb6>
b0: 1ce2 mov r0,r7
b2: 25e8 0001 b 2fc <___divsf3+0x2fc>
if (!aAbs) {
b6: 0833 sub r0,r2,0
b8: 0910 bne ca <___divsf3+0xca>
ba: 000b 0002 mov r0,0x0
be: 180b 17f2 movt r0,0x7fc0
c2: 3833 sub r1,r6,0
c4: 1c12 movne r0,r7
c6: 1be8 0001 b 2fc <___divsf3+0x2fc>
if (!bAbs) return fromRep(qnanRep);
// zero / anything else = +/- zero
else return fromRep(quotientSign);
}
// anything else / zero = +/- infinity
if (!bAbs) return fromRep(infRep | quotientSign);
ca: 7833 sub r3,r6,0
cc: 0510 bne d6 <___divsf3+0xd6>
ce: 1e7f 008a orr r0,r7,r12
d2: 15e8 0001 b 2fc <___divsf3+0x2fc>
// one or both of a or b is denormal, the other (if applicable) is a
// normal number. Renormalize one or both of a and b, and set scale to
// include the necessary exponent adjustment.
if (aAbs < implicitBit) scale += normalize(&aSignificand);
d6: 1feb 0ff2 mov r0,0xffff
da: 0feb 1002 movt r0,0x7f
de: 883f 200a sub r12,r2,r0
e2: 1220 bgtu 106 <___divsf3+0x106>
typedef float fp_t;
#define REP_C UINT32_C
#define significandBits 23
static inline int rep_clz(rep_t a) {
return __builtin_clz(a);
e4: 200b 0002 mov r1,0x0
e8: 04ef 0402 mov r0,r9
ec: 200b 1002 movt r1,0x0
f0: 8112 movfs r4,config
f2: 0552 jalr r1
}
static inline int normalize(rep_t *significand) {
const int shift = rep_clz(*significand) - rep_clz(implicitBit);
*significand <<= shift;
return 1 - shift;
f4: e12b 2002 mov r15,0x9
const union { fp_t f; rep_t i; } rep = {.i = x};
return rep.f;
}
static inline int normalize(rep_t *significand) {
const int shift = rep_clz(*significand) - rep_clz(implicitBit);
f8: 201b 00ff add r1,r0,-8
*significand <<= shift;
fc: 24af 240a lsl r9,r9,r1
return 1 - shift;
100: fc3f 240a sub r15,r15,r0
104: 04e0 b 10c <___divsf3+0x10c>
const unsigned int bExponent = toRep(b) >> significandBits & maxExponent;
const rep_t quotientSign = (toRep(a) ^ toRep(b)) & signBit;
rep_t aSignificand = toRep(a) & significandMask;
rep_t bSignificand = toRep(b) & significandMask;
int scale = 0;
106: e00b 2002 mov r15,0x0
10a: 8112 movfs r4,config
// one or both of a or b is denormal, the other (if applicable) is a
// normal number. Renormalize one or both of a and b, and set scale to
// include the necessary exponent adjustment.
if (aAbs < implicitBit) scale += normalize(&aSignificand);
if (bAbs < implicitBit) scale -= normalize(&bSignificand);
10c: 1feb 0ff2 mov r0,0xffff
110: 0feb 1002 movt r0,0x7f
114: 383a sub r1,r6,r0
116: 1420 bgtu 13e <___divsf3+0x13e>
typedef float fp_t;
#define REP_C UINT32_C
#define significandBits 23
static inline int rep_clz(rep_t a) {
return __builtin_clz(a);
118: 200b 0002 mov r1,0x0
11c: 00ef 0402 mov r0,r8
120: 200b 1002 movt r1,0x0
124: 0552 jalr r1
const union { fp_t f; rep_t i; } rep = {.i = x};
return rep.f;
}
static inline int normalize(rep_t *significand) {
const int shift = rep_clz(*significand) - rep_clz(implicitBit);
126: 201b 00ff add r1,r0,-8
*significand <<= shift;
return 1 - shift;
12a: fc1f 240a add r15,r15,r0
return rep.f;
}
static inline int normalize(rep_t *significand) {
const int shift = rep_clz(*significand) - rep_clz(implicitBit);
*significand <<= shift;
12e: 00af 240a lsl r8,r8,r1
132: ff9b 24fe add r15,r15,-9
136: 04e0 b 13e <___divsf3+0x13e>
const unsigned int bExponent = toRep(b) >> significandBits & maxExponent;
const rep_t quotientSign = (toRep(a) ^ toRep(b)) & signBit;
rep_t aSignificand = toRep(a) & significandMask;
rep_t bSignificand = toRep(b) & significandMask;
int scale = 0;
138: e00b 2002 mov r15,0x0
13c: 8112 movfs r4,config
}
// Or in the implicit significand bit. (If we fell through from the
// denormal path it was already set by normalize( ), but setting it twice
// wont hurt anything.)
aSignificand |= implicitBit;
13e: 000b 0002 mov r0,0x0
142: 100b 1002 movt r0,0x80
146: 047f 840a orr r32,r9,r0
bSignificand |= implicitBit;
int quotientExponent = aExponent - bExponent + scale;
14a: 4d3f 248a sub r10,fp,r10
// Or in the implicit significand bit. (If we fell through from the
// denormal path it was already set by normalize( ), but setting it twice
// wont hurt anything.)
aSignificand |= implicitBit;
bSignificand |= implicitBit;
14e: 007f 240a orr r8,r8,r0
// Align the significand of b as a Q31 fixed-point number in the range
// [1, 2.0) and get a Q32 approximate reciprocal using a small minimax
// polynomial approximation: reciprocal = 3/4 + 1/sqrt(2) - b/2. This
// is accurate to about 3.5 binary digits.
uint32_t q31b = bSignificand << 8;
uint32_t reciprocal = UINT32_C(0x7504f333) - q31b;
152: 266b 2f32 mov r9,0xf333
// Or in the implicit significand bit. (If we fell through from the
// denormal path it was already set by normalize( ), but setting it twice
// wont hurt anything.)
aSignificand |= implicitBit;
bSignificand |= implicitBit;
int quotientExponent = aExponent - bExponent + scale;
156: eb9f 248a add r15,r10,r15
// Align the significand of b as a Q31 fixed-point number in the range
// [1, 2.0) and get a Q32 approximate reciprocal using a small minimax
// polynomial approximation: reciprocal = 3/4 + 1/sqrt(2) - b/2. This
// is accurate to about 3.5 binary digits.
uint32_t q31b = bSignificand << 8;
uint32_t reciprocal = UINT32_C(0x7504f333) - q31b;
15a: 208b 3752 movt r9,0x7504
// Align the significand of b as a Q31 fixed-point number in the range
// [1, 2.0) and get a Q32 approximate reciprocal using a small minimax
// polynomial approximation: reciprocal = 3/4 + 1/sqrt(2) - b/2. This
// is accurate to about 3.5 binary digits.
uint32_t q31b = bSignificand << 8;
15e: 411f 2406 lsl r10,r8,0x8
uint32_t reciprocal = UINT32_C(0x7504f333) - q31b;
162: 253f 248a sub r9,r9,r10
//
// This doubles the number of correct binary digits in the approximation
// with each iteration, so after three iterations, we have about 28 binary
// digits of accuracy.
uint32_t correction;
correction = -((uint64_t)reciprocal * q31b >> 32);
166: c00b 0002 mov r6,0x0
16a: c00b 1002 movt r6,0x0
16e: 04ef 0402 mov r0,r9
172: 48ef 0402 mov r2,r10
176: 6003 mov r3,0x0
178: 2003 mov r1,0x0
17a: 1952 jalr r6
17c: 600b 2002 mov fp,0x0
reciprocal = (uint64_t)reciprocal * correction >> 31;
180: 0cbf 040a sub r0,fp,r1
184: 44ef 0402 mov r2,r9
188: 6003 mov r3,0x0
18a: 2003 mov r1,0x0
18c: 1952 jalr r6
18e: 2436 lsl r1,r1,0x1
190: 23ef 2006 lsr r9,r0,0x1f
194: 24ff 208a orr r9,r1,r9
correction = -((uint64_t)reciprocal * q31b >> 32);
198: 04ef 0402 mov r0,r9
19c: 48ef 0402 mov r2,r10
1a0: 6003 mov r3,0x0
1a2: 2003 mov r1,0x0
1a4: 1952 jalr r6
reciprocal = (uint64_t)reciprocal * correction >> 31;
1a6: 44ef 0402 mov r2,r9
1aa: 0cbf 040a sub r0,fp,r1
1ae: 6003 mov r3,0x0
1b0: 2003 mov r1,0x0
1b2: 1952 jalr r6
1b4: 2436 lsl r1,r1,0x1
1b6: 23ef 2006 lsr r9,r0,0x1f
1ba: 24ff 208a orr r9,r1,r9
correction = -((uint64_t)reciprocal * q31b >> 32);
1be: 48ef 0402 mov r2,r10
1c2: 6003 mov r3,0x0
1c4: 04ef 0402 mov r0,r9
1c8: 2003 mov r1,0x0
1ca: 1952 jalr r6
reciprocal = (uint64_t)reciprocal * correction >> 31;
1cc: 44ef 0402 mov r2,r9
1d0: 0cbf 040a sub r0,fp,r1
1d4: 6003 mov r3,0x0
1d6: 2003 mov r1,0x0
1d8: 1952 jalr r6
1da: 2436 lsl r1,r1,0x1
1dc: 03e6 lsr r0,r0,0x1f
1de: 047a orr r0,r1,r0
// 3. the error in q is at most 2^-24 + 2^-27 -- the 2^24 term comes
// from the fact that we truncate the product, and the 2^27 term
// is the error in the reciprocal of b scaled by the maximum
// possible value of a. As a consequence of this error bound,
// either q or nextafter(q) is the correctly rounded
rep_t quotient = (uint64_t)reciprocal*(aSignificand << 1) >> 32;
1e0: 0313 add r0,r0,-2
1e2: 403f 1006 lsl r2,r32,0x1
1e6: 2003 mov r1,0x0
1e8: 6003 mov r3,0x0
1ea: 1952 jalr r6
// if r is greater than 1/2 ulp(q)*b, then q rounds up. Otherwise, we
// already have the correct result. The exact halfway case cannot occur.
// We also take this time to right shift quotient if it falls in the [1,2)
// range and adjust the exponent accordingly.
rep_t residual;
if (quotient < (implicitBit << 1)) {
1ec: 1feb 0ff2 mov r0,0xffff
1f0: 1feb 1002 movt r0,0xff
//
// This doubles the number of correct binary digits in the approximation
// with each iteration, so after three iterations, we have about 28 binary
// digits of accuracy.
uint32_t correction;
correction = -((uint64_t)reciprocal * q31b >> 32);
1f4: bfcb 0ff2 mov r5,0xfffe
// if r is greater than 1/2 ulp(q)*b, then q rounds up. Otherwise, we
// already have the correct result. The exact halfway case cannot occur.
// We also take this time to right shift quotient if it falls in the [1,2)
// range and adjust the exponent accordingly.
rep_t residual;
if (quotient < (implicitBit << 1)) {
1f8: 443a sub r2,r1,r0
//
// This doubles the number of correct binary digits in the approximation
// with each iteration, so after three iterations, we have about 28 binary
// digits of accuracy.
uint32_t correction;
correction = -((uint64_t)reciprocal * q31b >> 32);
1fa: be2b 1ff2 movt r5,0xfff1
// if r is greater than 1/2 ulp(q)*b, then q rounds up. Otherwise, we
// already have the correct result. The exact halfway case cannot occur.
// We also take this time to right shift quotient if it falls in the [1,2)
// range and adjust the exponent accordingly.
rep_t residual;
if (quotient < (implicitBit << 1)) {
1fe: 1b20 bgtu 234 <___divsf3+0x234>
residual = (aSignificand << 24) - quotient * bSignificand;
200: 400b 0002 mov r2,0x0
204: 031f 9006 lsl r32,r32,0x18
208: 410b 1002 movt r2,0x8
20c: 0392 gid
20e: 6112 movfs r3,config
210: 6d7a orr r3,r3,r2
212: 6102 movts config,r3
214: 0192 gie
216: 0392 gid
218: 811f 2002 movfs r12,config
21c: 917f 240a orr r12,r12,r2
220: 810f 2002 movts config,r12
224: 0192 gie
226: 042f 0087 fmul r0,r1,r8
quotientExponent--;
22a: ff9b 24ff add r15,r15,-1
// already have the correct result. The exact halfway case cannot occur.
// We also take this time to right shift quotient if it falls in the [1,2)
// range and adjust the exponent accordingly.
rep_t residual;
if (quotient < (implicitBit << 1)) {
residual = (aSignificand << 24) - quotient * bSignificand;
22e: 003f 900a sub r32,r32,r0
232: 19e0 b 264 <___divsf3+0x264>
quotientExponent--;
} else {
quotient >>= 1;
residual = (aSignificand << 23) - quotient * bSignificand;
234: 400b 0002 mov r2,0x0
rep_t residual;
if (quotient < (implicitBit << 1)) {
residual = (aSignificand << 24) - quotient * bSignificand;
quotientExponent--;
} else {
quotient >>= 1;
238: 2426 lsr r1,r1,0x1
residual = (aSignificand << 23) - quotient * bSignificand;
23a: 02ff 9006 lsl r32,r32,0x17
23e: 410b 1002 movt r2,0x8
242: 0392 gid
244: 811f 2002 movfs r12,config
248: 917f 240a orr r12,r12,r2
24c: 810f 2002 movts config,r12
250: 0192 gie
252: 0392 gid
254: 6112 movfs r3,config
256: 6d7a orr r3,r3,r2
258: 6102 movts config,r3
25a: 0192 gie
25c: 042f 0087 fmul r0,r1,r8
260: 003f 900a sub r32,r32,r0
}
const int writtenExponent = quotientExponent + exponentBias;
264: ff9b 240f add r15,r15,127
if (writtenExponent >= maxExponent) {
268: 7f3b 041f sub r3,r15,254
26c: 1e90 blte 2a8 <___divsf3+0x2a8>
return rep.i;
}
static inline fp_t fromRep(rep_t x) {
const union { fp_t f; rep_t i; } rep = {.i = x};
return rep.f;
26e: 000b 0002 mov r0,0x0
272: 100b 17f2 movt r0,0x7f80
276: 1c7a orr r0,r7,r0
278: 0392 gid
27a: 811f 2002 movfs r12,config
27e: 920f 240a eor r12,r12,r4
282: 92df 240a and r12,r12,r5
286: 920f 240a eor r12,r12,r4
28a: 810f 2002 movts config,r12
28e: 0192 gie
290: 0392 gid
292: 811f 2002 movfs r12,config
296: 920f 240a eor r12,r12,r4
29a: 92df 240a and r12,r12,r5
29e: 920f 240a eor r12,r12,r4
2a2: 810f 2002 movts config,r12
2a6: 25e0 b 2f0 <___divsf3+0x2f0>
// If we have overflowed the exponent, return infinity.
return fromRep(infRep | quotientSign);
}
else if (writtenExponent < 1) {
2a8: 9c3b 2400 sub r12,r15,0
2ac: 0360 bgt 2b2 <___divsf3+0x2b2>
2ae: 1ce2 mov r0,r7
2b0: 13e0 b 2d6 <___divsf3+0x2d6>
}
else {
const bool round = (residual << 1) > bSignificand;
// Clear the implicit bit
rep_t absResult = quotient & significandMask;
2b2: 1feb 0ff2 mov r0,0xffff
2b6: 0feb 1002 movt r0,0x7f
2ba: 245a and r1,r1,r0
// Insert the exponent
absResult |= (rep_t)writtenExponent << significandBits;
2bc: feff 2406 lsl r15,r15,0x17
2c0: 1cff 040a orr r0,r15,r1
// code to round them correctly.
return fromRep(quotientSign);
}
else {
const bool round = (residual << 1) > bSignificand;
2c4: 003f 9006 lsl r32,r32,0x1
2c8: 203f 108a sub r1,r32,r8
2cc: 4003 mov r2,0x0
2ce: 2023 mov r1,0x1
2d0: 4422 movgtu r2,r1
// Clear the implicit bit
rep_t absResult = quotient & significandMask;
// Insert the exponent
absResult |= (rep_t)writtenExponent << significandBits;
// Round
absResult += round;
2d2: 011a add r0,r0,r2
2d4: 03fa orr r0,r0,r7
2d6: 0392 gid
2d8: 4112 movfs r2,config
2da: 4a0a eor r2,r2,r4
2dc: 4ada and r2,r2,r5
2de: 4a0a eor r2,r2,r4
2e0: 4102 movts config,r2
2e2: 0192 gie
2e4: 0392 gid
2e6: 4112 movfs r2,config
2e8: 4a0a eor r2,r2,r4
2ea: 4ada and r2,r2,r5
2ec: 4a0a eor r2,r2,r4
2ee: 4102 movts config,r2
2f0: 0192 gie
// Insert the sign and return
return fromRep(absResult | quotientSign);
2f2: 05e0 b 2fc <___divsf3+0x2fc>
// anything / NaN = qNaN
if (bAbs > infRep) return fromRep(toRep(b) | quietBit);
if (aAbs == infRep) {
// infinity / infinity = NaN
if (bAbs == infRep) return fromRep(qnanRep);
2f4: 000b 0002 mov r0,0x0
2f8: 180b 17f2 movt r0,0x7fc0
// Round
absResult += round;
// Insert the sign and return
return fromRep(absResult | quotientSign);
}
}
2fc: d6ec 0400 ldrd r6,[sp,+0x5]
300: 166c 2400 ldrd r8,[sp,+0x4]
304: 55ec 2400 ldrd r10,[sp,+0x3]
308: d56c 2400 ldrd lr,[sp,+0x2]
30c: 15cc 8400 ldr r32,[sp,+0x3]
310: b41b 2406 add sp,sp,48
314: 946c 0400 ldrd r4,[sp,+0x0]
318: 194f 0402 rts
_div_sf.o: file format elf32-epiphany
_div_sf.o
architecture: epiphany32, flags 0x00000011:
HAS_RELOC, HAS_SYMS
start address 0x00000000
Sections:
Idx Name Size VMA LMA File off Algn
0 .text 00000120 00000000 00000000 00000034 2**2
CONTENTS, ALLOC, LOAD, RELOC, READONLY, CODE
1 .data 00000000 00000000 00000000 00000154 2**0
CONTENTS, ALLOC, LOAD, DATA
2 .bss 00000000 00000000 00000000 00000154 2**0
ALLOC
3 .debug_frame 00000034 00000000 00000000 00000154 2**2
CONTENTS, RELOC, READONLY, DEBUGGING
4 .debug_info 000003a9 00000000 00000000 00000188 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
5 .debug_abbrev 000001f5 00000000 00000000 00000531 2**0
CONTENTS, READONLY, DEBUGGING
6 .debug_loc 000000f2 00000000 00000000 00000726 2**0
CONTENTS, READONLY, DEBUGGING
7 .debug_aranges 00000020 00000000 00000000 00000818 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
8 .debug_ranges 00000018 00000000 00000000 00000838 2**0
CONTENTS, READONLY, DEBUGGING
9 .debug_line 00000212 00000000 00000000 00000850 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
10 .debug_str 000002d7 00000000 00000000 00000a62 2**0
CONTENTS, READONLY, DEBUGGING
11 .comment 0000003e 00000000 00000000 00000d39 2**0
CONTENTS, READONLY
SYMBOL TABLE:
00000000 l df *ABS* 00000000 fp-bit.c
00000000 l d .text 00000000 .text
00000000 l d .data 00000000 .data
00000000 l d .bss 00000000 .bss
00000000 l d .debug_frame 00000000 .debug_frame
00000000 l d .debug_info 00000000 .debug_info
00000000 l d .debug_abbrev 00000000 .debug_abbrev
00000000 l d .debug_loc 00000000 .debug_loc
00000000 l d .debug_aranges 00000000 .debug_aranges
00000000 l d .debug_ranges 00000000 .debug_ranges
00000000 l d .debug_line 00000000 .debug_line
00000000 l d .debug_str 00000000 .debug_str
0000005d l .debug_str 00000000 .LASF40
000001ca l .debug_str 00000000 .LASF41
0000017a l .debug_str 00000000 .LASF42
0000014b l .debug_str 00000000 .LASF0
00000128 l .debug_str 00000000 .LASF1
00000278 l .debug_str 00000000 .LASF2
0000029e l .debug_str 00000000 .LASF3
000002b1 l .debug_str 00000000 .LASF7
00000173 l .debug_str 00000000 .LASF4
00000202 l .debug_str 00000000 .LASF5
00000000 l .debug_str 00000000 .LASF6
0000025b l .debug_str 00000000 .LASF8
00000151 l .debug_str 00000000 .LASF9
00000107 l .debug_str 00000000 .LASF10
00000229 l .debug_str 00000000 .LASF11
00000217 l .debug_str 00000000 .LASF12
00000041 l .debug_str 00000000 .LASF13
00000220 l .debug_str 00000000 .LASF14
00000250 l .debug_str 00000000 .LASF15
0000011d l .debug_str 00000000 .LASF16
0000001b l .debug_str 00000000 .LASF17
000002b8 l .debug_str 00000000 .LASF18
00000285 l .debug_str 00000000 .LASF19
0000010f l .debug_str 00000000 .LASF20
00000240 l .debug_str 00000000 .LASF21
000002c5 l .debug_str 00000000 .LASF22
000002a7 l .debug_str 00000000 .LASF23
0000020c l .debug_str 00000000 .LASF24
0000004e l .debug_str 00000000 .LASF25
00000263 l .debug_str 00000000 .LASF26
00000272 l .debug_str 00000000 .LASF27
000001c0 l .debug_str 00000000 .LASF28
000002ac l .debug_str 00000000 .LASF29
00000164 l .debug_str 00000000 .LASF30
00000249 l .debug_str 00000000 .LASF31
00000026 l .debug_str 00000000 .LASF32
00000057 l .debug_str 00000000 .LASF33
0000000e l .debug_str 00000000 .LASF34
00000294 l .debug_str 00000000 .LASF35
000002cb l .debug_str 00000000 .LASF36
00000038 l .debug_str 00000000 .LASF37
000000ff l .debug_str 00000000 .LASF43
00000136 l .debug_str 00000000 .LASF44
0000013f l .debug_str 00000000 .LASF38
00000145 l .debug_str 00000000 .LASF39
0000002c l .debug_str 00000000 .LASF45
00000000 l d .comment 00000000 .comment
00000000 g .text 00000120 .hidden ___divsf3
00000000 *UND* 00000000 ___unpack_f
00000000 *UND* 00000000 ___thenan_sf
00000000 *UND* 00000000 ___pack_f
Disassembly of section .text:
00000000 <___divsf3>:
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
0: 975c 0701 str r4,[sp],-0xe
FLO_union_type au, bu;
au.value = arg_a;
bu.value = arg_b;
unpack_d (&au, &a);
4: 800b 0002 mov r4,0x0
4: R_EPIPHANY_LOW ___unpack_f
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
8: d6dc 2401 str lr,[sp,+0xd]
fp_number_type a;
fp_number_type b;
const fp_number_type *res;
FLO_union_type au, bu;
au.value = arg_a;
c: 155c 0400 str r0,[sp,+0x2]
bu.value = arg_b;
10: 35dc 0400 str r1,[sp,+0x3]
unpack_d (&au, &a);
14: 141b 0401 add r0,sp,8
18: 341b 0402 add r1,sp,16
1c: 800b 1002 movt r4,0x0
1c: R_EPIPHANY_HIGH ___unpack_f
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
20: 77dc 2401 str fp,[sp,+0xf]
FLO_union_type au, bu;
au.value = arg_a;
bu.value = arg_b;
unpack_d (&au, &a);
24: 1152 jalr r4
unpack_d (&bu, &b);
26: 341b 0404 add r1,sp,32
2a: 161b 0401 add r0,sp,12
2e: 1152 jalr r4
30: 364c 0400 ldr r1,[sp,+0x4]
fractype bit;
fractype numerator;
fractype denominator;
fractype quotient;
if (isnan (a))
34: 04b3 sub r0,r1,1
36: 5b40 blteu ec <___divsf3+0xec>
38: 144c 0401 ldr r0,[sp,+0x8]
{
return a;
}
if (isnan (b))
3c: 40b3 sub r2,r0,1
3e: 5a40 blteu f2 <___divsf3+0xf2>
{
return b;
}
a->sign = a->sign ^ b->sign;
40: 76cc 0400 ldr r3,[sp,+0x5]
44: 54cc 0401 ldr r2,[sp,+0x9]
48: 4d0a eor r2,r3,r2
4a: 56dc 0400 str r2,[sp,+0x5]
if (isinf (a) || iszero (a))
4e: 663b 0000 sub r3,r1,4
52: 0400 beq 5a <___divsf3+0x5a>
54: 053b 4000 sub r16,r1,2
58: 0410 bne 60 <___divsf3+0x60>
{
if (a->class == b->class)
5a: 443a sub r2,r1,r0
5c: 4810 bne ec <___divsf3+0xec>
5e: 4ee0 b fa <___divsf3+0xfa>
return makenan ();
return a;
}
if (isinf (b))
60: 623b 0000 sub r3,r0,4
64: 0710 bne 72 <___divsf3+0x72>
{
a->fraction.ll = 0;
66: 0003 mov r0,0x0
68: 17dc 0400 str r0,[sp,+0x7]
a->normal_exp = 0;
6c: 175c 0400 str r0,[sp,+0x6]
70: 07e0 b 7e <___divsf3+0x7e>
return a;
}
if (iszero (b))
72: 013b 4000 sub r16,r0,2
76: 0610 bne 82 <___divsf3+0x82>
{
a->class = CLASS_INFINITY;
78: 0083 mov r0,0x4
7a: 165c 0400 str r0,[sp,+0x4]
return a;
7e: 0203 mov r0,0x10
80: 3ae0 b f4 <___divsf3+0xf4>
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
82: 154c 0401 ldr r0,[sp,+0xa]
86: 374c 0400 ldr r1,[sp,+0x6]
numerator = a->fraction.ll;
denominator = b->fraction.ll;
8a: 95cc 2401 ldr r12,[sp,+0xb]
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
8e: 243a sub r1,r1,r0
numerator = a->fraction.ll;
90: 17cc 0400 ldr r0,[sp,+0x7]
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
94: 375c 0400 str r1,[sp,+0x6]
numerator = a->fraction.ll;
denominator = b->fraction.ll;
if (numerator < denominator)
98: 423f 008a sub r2,r0,r12
9c: 0530 bgteu a6 <___divsf3+0xa6>
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a->normal_exp--;
9e: 2793 add r1,r1,-1
denominator = b->fraction.ll;
if (numerator < denominator)
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a0: 0036 lsl r0,r0,0x1
a->normal_exp--;
a2: 375c 0400 str r1,[sp,+0x6]
}
bit = IMPLICIT_1;
a6: 600b 0002 mov r3,0x0
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
aa: 43e3 mov r2,0x1f
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a->normal_exp--;
}
bit = IMPLICIT_1;
ac: 600b 1402 movt r3,0x4000
quotient = 0;
b0: 2003 mov r1,0x0
/* ??? Does divide one bit at a time. Optimize. */
while (bit)
{
if (numerator >= denominator)
b2: 023f 408a sub r16,r0,r12
b6: 0450 bltu be <___divsf3+0xbe>
{
quotient |= bit;
b8: 25fa orr r1,r1,r3
numerator -= denominator;
ba: 023f 008a sub r0,r0,r12
}
bit >>= 1;
be: 6c26 lsr r3,r3,0x1
numerator *= 2;
c0: 0036 lsl r0,r0,0x1
a->normal_exp--;
}
bit = IMPLICIT_1;
quotient = 0;
/* ??? Does divide one bit at a time. Optimize. */
while (bit)
c2: 48b3 sub r2,r2,1
c4: f710 bne b2 <___divsf3+0xb2>
}
bit >>= 1;
numerator *= 2;
}
if (!ROUND_TOWARDS_ZERO && (quotient & GARDMASK) == GARDMSB)
c6: 4fe3 mov r2,0x7f
c8: 455a and r2,r1,r2
ca: 683b 0008 sub r3,r2,64
ce: 0d10 bne e8 <___divsf3+0xe8>
{
if (quotient & (1 << NGARDS))
d0: 071f 4006 lsl r16,r1,0x18
d4: 0a80 blt e8 <___divsf3+0xe8>
/* Because we re half way, we would round to even by adding
GARDROUND + 1, except thats also done in the packing
function, and rounding twice will lose precision and cause
the result to be too far off. */
}
else if (numerator)
d6: 4033 sub r2,r0,0
d8: 0800 beq e8 <___divsf3+0xe8>
that, we round here and not in pack_d, because there we
dont have "numerator" available anymore. */
quotient += GARDROUND + 1;
/* Avoid further rounding in pack_d. */
quotient &= ~(fractype) GARDMASK;
da: 100b 0ff2 mov r0,0xff80
{
/* We re a further than half way by the small amount
corresponding to the bits set in "numerator". Knowing
that, we round here and not in pack_d, because there we
don t have "numerator" available anymore. */
quotient += GARDROUND + 1;
de: 241b 0008 add r1,r1,64
/* Avoid further rounding in pack_d. */
quotient &= ~(fractype) GARDMASK;
e2: 1feb 1ff2 movt r0,0xffff
e6: 245a and r1,r1,r0
}
}
a->fraction.ll = quotient;
e8: 37dc 0400 str r1,[sp,+0x7]
return (a);
ec: 141b 0402 add r0,sp,16
f0: 09e0 b 102 <___divsf3+0x102>
{
return a;
}
if (isnan (b))
{
return b;
f2: 0403 mov r0,0x20
f4: 029f 008a add r0,r0,sp
f8: 05e0 b 102 <___divsf3+0x102>
a->sign = a->sign ^ b->sign;
if (isinf (a) || iszero (a))
{
if (a->class == b->class)
return makenan ();
fa: 000b 0002 mov r0,0x0
fa: R_EPIPHANY_LOW ___thenan_sf
fe: 000b 1002 movt r0,0x0
fe: R_EPIPHANY_HIGH ___thenan_sf
unpack_d (&au, &a);
unpack_d (&bu, &b);
res = _fpdiv_parts (&a, &b);
return pack_d (res);
102: 200b 0002 mov r1,0x0
102: R_EPIPHANY_LOW ___pack_f
106: 200b 1002 movt r1,0x0
106: R_EPIPHANY_HIGH ___pack_f
10a: 0552 jalr r1
}
10c: 77cc 2401 ldr fp,[sp,+0xf]
110: 974c 0401 ldr r4,[sp,+0xe]
114: d6cc 2401 ldr lr,[sp,+0xd]
118: b41b 2407 add sp,sp,56
11c: 194f 0402 rts
_div_sf.o: file format elf32-epiphany
_div_sf.o
architecture: epiphany32, flags 0x00000011:
HAS_RELOC, HAS_SYMS
start address 0x00000000
Sections:
Idx Name Size VMA LMA File off Algn
0 .text 00000120 00000000 00000000 00000034 2**2
CONTENTS, ALLOC, LOAD, RELOC, READONLY, CODE
1 .data 00000000 00000000 00000000 00000154 2**0
CONTENTS, ALLOC, LOAD, DATA
2 .bss 00000000 00000000 00000000 00000154 2**0
ALLOC
3 .debug_frame 00000034 00000000 00000000 00000154 2**2
CONTENTS, RELOC, READONLY, DEBUGGING
4 .debug_info 000003a9 00000000 00000000 00000188 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
5 .debug_abbrev 000001f5 00000000 00000000 00000531 2**0
CONTENTS, READONLY, DEBUGGING
6 .debug_loc 000000f2 00000000 00000000 00000726 2**0
CONTENTS, READONLY, DEBUGGING
7 .debug_aranges 00000020 00000000 00000000 00000818 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
8 .debug_ranges 00000018 00000000 00000000 00000838 2**0
CONTENTS, READONLY, DEBUGGING
9 .debug_line 00000212 00000000 00000000 00000850 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
10 .debug_str 000002d7 00000000 00000000 00000a62 2**0
CONTENTS, READONLY, DEBUGGING
11 .comment 0000003e 00000000 00000000 00000d39 2**0
CONTENTS, READONLY
SYMBOL TABLE:
00000000 l df *ABS* 00000000 fp-bit.c
00000000 l d .text 00000000 .text
00000000 l d .data 00000000 .data
00000000 l d .bss 00000000 .bss
00000000 l d .debug_frame 00000000 .debug_frame
00000000 l d .debug_info 00000000 .debug_info
00000000 l d .debug_abbrev 00000000 .debug_abbrev
00000000 l d .debug_loc 00000000 .debug_loc
00000000 l d .debug_aranges 00000000 .debug_aranges
00000000 l d .debug_ranges 00000000 .debug_ranges
00000000 l d .debug_line 00000000 .debug_line
00000000 l d .debug_str 00000000 .debug_str
0000005d l .debug_str 00000000 .LASF40
000001ca l .debug_str 00000000 .LASF41
0000017a l .debug_str 00000000 .LASF42
0000014b l .debug_str 00000000 .LASF0
00000128 l .debug_str 00000000 .LASF1
00000278 l .debug_str 00000000 .LASF2
0000029e l .debug_str 00000000 .LASF3
000002b1 l .debug_str 00000000 .LASF7
00000173 l .debug_str 00000000 .LASF4
00000202 l .debug_str 00000000 .LASF5
00000000 l .debug_str 00000000 .LASF6
0000025b l .debug_str 00000000 .LASF8
00000151 l .debug_str 00000000 .LASF9
00000107 l .debug_str 00000000 .LASF10
00000229 l .debug_str 00000000 .LASF11
00000217 l .debug_str 00000000 .LASF12
00000041 l .debug_str 00000000 .LASF13
00000220 l .debug_str 00000000 .LASF14
00000250 l .debug_str 00000000 .LASF15
0000011d l .debug_str 00000000 .LASF16
0000001b l .debug_str 00000000 .LASF17
000002b8 l .debug_str 00000000 .LASF18
00000285 l .debug_str 00000000 .LASF19
0000010f l .debug_str 00000000 .LASF20
00000240 l .debug_str 00000000 .LASF21
000002c5 l .debug_str 00000000 .LASF22
000002a7 l .debug_str 00000000 .LASF23
0000020c l .debug_str 00000000 .LASF24
0000004e l .debug_str 00000000 .LASF25
00000263 l .debug_str 00000000 .LASF26
00000272 l .debug_str 00000000 .LASF27
000001c0 l .debug_str 00000000 .LASF28
000002ac l .debug_str 00000000 .LASF29
00000164 l .debug_str 00000000 .LASF30
00000249 l .debug_str 00000000 .LASF31
00000026 l .debug_str 00000000 .LASF32
00000057 l .debug_str 00000000 .LASF33
0000000e l .debug_str 00000000 .LASF34
00000294 l .debug_str 00000000 .LASF35
000002cb l .debug_str 00000000 .LASF36
00000038 l .debug_str 00000000 .LASF37
000000ff l .debug_str 00000000 .LASF43
00000136 l .debug_str 00000000 .LASF44
0000013f l .debug_str 00000000 .LASF38
00000145 l .debug_str 00000000 .LASF39
0000002c l .debug_str 00000000 .LASF45
00000000 l d .comment 00000000 .comment
00000000 g .text 00000120 .hidden ___divsf3
00000000 *UND* 00000000 ___unpack_f
00000000 *UND* 00000000 ___thenan_sf
00000000 *UND* 00000000 ___pack_f
Disassembly of section .text:
00000000 <___divsf3>:
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
0: 975c 0701 str r4,[sp],-0xe
FLO_union_type au, bu;
au.value = arg_a;
bu.value = arg_b;
unpack_d (&au, &a);
4: 800b 0002 mov r4,0x0
4: R_EPIPHANY_LOW ___unpack_f
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
8: d6dc 2401 str lr,[sp,+0xd]
fp_number_type a;
fp_number_type b;
const fp_number_type *res;
FLO_union_type au, bu;
au.value = arg_a;
c: 155c 0400 str r0,[sp,+0x2]
bu.value = arg_b;
10: 35dc 0400 str r1,[sp,+0x3]
unpack_d (&au, &a);
14: 141b 0401 add r0,sp,8
18: 341b 0402 add r1,sp,16
1c: 800b 1002 movt r4,0x0
1c: R_EPIPHANY_HIGH ___unpack_f
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
20: 77dc 2401 str fp,[sp,+0xf]
FLO_union_type au, bu;
au.value = arg_a;
bu.value = arg_b;
unpack_d (&au, &a);
24: 1152 jalr r4
unpack_d (&bu, &b);
26: 341b 0404 add r1,sp,32
2a: 161b 0401 add r0,sp,12
2e: 1152 jalr r4
30: 364c 0400 ldr r1,[sp,+0x4]
fractype bit;
fractype numerator;
fractype denominator;
fractype quotient;
if (isnan (a))
34: 04b3 sub r0,r1,1
36: 5b40 blteu ec <___divsf3+0xec>
38: 144c 0401 ldr r0,[sp,+0x8]
{
return a;
}
if (isnan (b))
3c: 40b3 sub r2,r0,1
3e: 5a40 blteu f2 <___divsf3+0xf2>
{
return b;
}
a->sign = a->sign ^ b->sign;
40: 76cc 0400 ldr r3,[sp,+0x5]
44: 54cc 0401 ldr r2,[sp,+0x9]
48: 4d0a eor r2,r3,r2
4a: 56dc 0400 str r2,[sp,+0x5]
if (isinf (a) || iszero (a))
4e: 663b 0000 sub r3,r1,4
52: 0400 beq 5a <___divsf3+0x5a>
54: 053b 4000 sub r16,r1,2
58: 0410 bne 60 <___divsf3+0x60>
{
if (a->class == b->class)
5a: 443a sub r2,r1,r0
5c: 4810 bne ec <___divsf3+0xec>
5e: 4ee0 b fa <___divsf3+0xfa>
return makenan ();
return a;
}
if (isinf (b))
60: 623b 0000 sub r3,r0,4
64: 0710 bne 72 <___divsf3+0x72>
{
a->fraction.ll = 0;
66: 0003 mov r0,0x0
68: 17dc 0400 str r0,[sp,+0x7]
a->normal_exp = 0;
6c: 175c 0400 str r0,[sp,+0x6]
70: 07e0 b 7e <___divsf3+0x7e>
return a;
}
if (iszero (b))
72: 013b 4000 sub r16,r0,2
76: 0610 bne 82 <___divsf3+0x82>
{
a->class = CLASS_INFINITY;
78: 0083 mov r0,0x4
7a: 165c 0400 str r0,[sp,+0x4]
return a;
7e: 0203 mov r0,0x10
80: 3ae0 b f4 <___divsf3+0xf4>
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
82: 154c 0401 ldr r0,[sp,+0xa]
86: 374c 0400 ldr r1,[sp,+0x6]
numerator = a->fraction.ll;
denominator = b->fraction.ll;
8a: 95cc 2401 ldr r12,[sp,+0xb]
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
8e: 243a sub r1,r1,r0
numerator = a->fraction.ll;
90: 17cc 0400 ldr r0,[sp,+0x7]
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
94: 375c 0400 str r1,[sp,+0x6]
numerator = a->fraction.ll;
denominator = b->fraction.ll;
if (numerator < denominator)
98: 423f 008a sub r2,r0,r12
9c: 0530 bgteu a6 <___divsf3+0xa6>
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a->normal_exp--;
9e: 2793 add r1,r1,-1
denominator = b->fraction.ll;
if (numerator < denominator)
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a0: 0036 lsl r0,r0,0x1
a->normal_exp--;
a2: 375c 0400 str r1,[sp,+0x6]
}
bit = IMPLICIT_1;
a6: 600b 0002 mov r3,0x0
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
aa: 43e3 mov r2,0x1f
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a->normal_exp--;
}
bit = IMPLICIT_1;
ac: 600b 1402 movt r3,0x4000
quotient = 0;
b0: 2003 mov r1,0x0
/* ??? Does divide one bit at a time. Optimize. */
while (bit)
{
if (numerator >= denominator)
b2: 023f 408a sub r16,r0,r12
b6: 0450 bltu be <___divsf3+0xbe>
{
quotient |= bit;
b8: 25fa orr r1,r1,r3
numerator -= denominator;
ba: 023f 008a sub r0,r0,r12
}
bit >>= 1;
be: 6c26 lsr r3,r3,0x1
numerator *= 2;
c0: 0036 lsl r0,r0,0x1
a->normal_exp--;
}
bit = IMPLICIT_1;
quotient = 0;
/* ??? Does divide one bit at a time. Optimize. */
while (bit)
c2: 48b3 sub r2,r2,1
c4: f710 bne b2 <___divsf3+0xb2>
}
bit >>= 1;
numerator *= 2;
}
if (!ROUND_TOWARDS_ZERO && (quotient & GARDMASK) == GARDMSB)
c6: 4fe3 mov r2,0x7f
c8: 455a and r2,r1,r2
ca: 683b 0008 sub r3,r2,64
ce: 0d10 bne e8 <___divsf3+0xe8>
{
if (quotient & (1 << NGARDS))
d0: 071f 4006 lsl r16,r1,0x18
d4: 0a80 blt e8 <___divsf3+0xe8>
/* Because we re half way, we would round to even by adding
GARDROUND + 1, except thats also done in the packing
function, and rounding twice will lose precision and cause
the result to be too far off. */
}
else if (numerator)
d6: 4033 sub r2,r0,0
d8: 0800 beq e8 <___divsf3+0xe8>
that, we round here and not in pack_d, because there we
dont have "numerator" available anymore. */
quotient += GARDROUND + 1;
/* Avoid further rounding in pack_d. */
quotient &= ~(fractype) GARDMASK;
da: 100b 0ff2 mov r0,0xff80
{
/* We re a further than half way by the small amount
corresponding to the bits set in "numerator". Knowing
that, we round here and not in pack_d, because there we
don t have "numerator" available anymore. */
quotient += GARDROUND + 1;
de: 241b 0008 add r1,r1,64
/* Avoid further rounding in pack_d. */
quotient &= ~(fractype) GARDMASK;
e2: 1feb 1ff2 movt r0,0xffff
e6: 245a and r1,r1,r0
}
}
a->fraction.ll = quotient;
e8: 37dc 0400 str r1,[sp,+0x7]
return (a);
ec: 141b 0402 add r0,sp,16
f0: 09e0 b 102 <___divsf3+0x102>
{
return a;
}
if (isnan (b))
{
return b;
f2: 0403 mov r0,0x20
f4: 029f 008a add r0,r0,sp
f8: 05e0 b 102 <___divsf3+0x102>
a->sign = a->sign ^ b->sign;
if (isinf (a) || iszero (a))
{
if (a->class == b->class)
return makenan ();
fa: 000b 0002 mov r0,0x0
fa: R_EPIPHANY_LOW ___thenan_sf
fe: 000b 1002 movt r0,0x0
fe: R_EPIPHANY_HIGH ___thenan_sf
unpack_d (&au, &a);
unpack_d (&bu, &b);
res = _fpdiv_parts (&a, &b);
return pack_d (res);
102: 200b 0002 mov r1,0x0
102: R_EPIPHANY_LOW ___pack_f
106: 200b 1002 movt r1,0x0
106: R_EPIPHANY_HIGH ___pack_f
10a: 0552 jalr r1
}
10c: 77cc 2401 ldr fp,[sp,+0xf]
110: 974c 0401 ldr r4,[sp,+0xe]
114: d6cc 2401 ldr lr,[sp,+0xd]
118: b41b 2407 add sp,sp,56
11c: 194f 0402 rts
_div_sf.o: file format elf32-epiphany
_div_sf.o
architecture: epiphany32, flags 0x00000011:
HAS_RELOC, HAS_SYMS
start address 0x00000000
Sections:
Idx Name Size VMA LMA File off Algn
0 .text 00000120 00000000 00000000 00000034 2**2
CONTENTS, ALLOC, LOAD, RELOC, READONLY, CODE
1 .data 00000000 00000000 00000000 00000154 2**0
CONTENTS, ALLOC, LOAD, DATA
2 .bss 00000000 00000000 00000000 00000154 2**0
ALLOC
3 .debug_frame 00000034 00000000 00000000 00000154 2**2
CONTENTS, RELOC, READONLY, DEBUGGING
4 .debug_info 000003a9 00000000 00000000 00000188 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
5 .debug_abbrev 000001f5 00000000 00000000 00000531 2**0
CONTENTS, READONLY, DEBUGGING
6 .debug_loc 000000f2 00000000 00000000 00000726 2**0
CONTENTS, READONLY, DEBUGGING
7 .debug_aranges 00000020 00000000 00000000 00000818 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
8 .debug_ranges 00000018 00000000 00000000 00000838 2**0
CONTENTS, READONLY, DEBUGGING
9 .debug_line 00000212 00000000 00000000 00000850 2**0
CONTENTS, RELOC, READONLY, DEBUGGING
10 .debug_str 000002d7 00000000 00000000 00000a62 2**0
CONTENTS, READONLY, DEBUGGING
11 .comment 0000003e 00000000 00000000 00000d39 2**0
CONTENTS, READONLY
SYMBOL TABLE:
00000000 l df *ABS* 00000000 fp-bit.c
00000000 l d .text 00000000 .text
00000000 l d .data 00000000 .data
00000000 l d .bss 00000000 .bss
00000000 l d .debug_frame 00000000 .debug_frame
00000000 l d .debug_info 00000000 .debug_info
00000000 l d .debug_abbrev 00000000 .debug_abbrev
00000000 l d .debug_loc 00000000 .debug_loc
00000000 l d .debug_aranges 00000000 .debug_aranges
00000000 l d .debug_ranges 00000000 .debug_ranges
00000000 l d .debug_line 00000000 .debug_line
00000000 l d .debug_str 00000000 .debug_str
0000005d l .debug_str 00000000 .LASF40
000001ca l .debug_str 00000000 .LASF41
0000017a l .debug_str 00000000 .LASF42
0000014b l .debug_str 00000000 .LASF0
00000128 l .debug_str 00000000 .LASF1
00000278 l .debug_str 00000000 .LASF2
0000029e l .debug_str 00000000 .LASF3
000002b1 l .debug_str 00000000 .LASF7
00000173 l .debug_str 00000000 .LASF4
00000202 l .debug_str 00000000 .LASF5
00000000 l .debug_str 00000000 .LASF6
0000025b l .debug_str 00000000 .LASF8
00000151 l .debug_str 00000000 .LASF9
00000107 l .debug_str 00000000 .LASF10
00000229 l .debug_str 00000000 .LASF11
00000217 l .debug_str 00000000 .LASF12
00000041 l .debug_str 00000000 .LASF13
00000220 l .debug_str 00000000 .LASF14
00000250 l .debug_str 00000000 .LASF15
0000011d l .debug_str 00000000 .LASF16
0000001b l .debug_str 00000000 .LASF17
000002b8 l .debug_str 00000000 .LASF18
00000285 l .debug_str 00000000 .LASF19
0000010f l .debug_str 00000000 .LASF20
00000240 l .debug_str 00000000 .LASF21
000002c5 l .debug_str 00000000 .LASF22
000002a7 l .debug_str 00000000 .LASF23
0000020c l .debug_str 00000000 .LASF24
0000004e l .debug_str 00000000 .LASF25
00000263 l .debug_str 00000000 .LASF26
00000272 l .debug_str 00000000 .LASF27
000001c0 l .debug_str 00000000 .LASF28
000002ac l .debug_str 00000000 .LASF29
00000164 l .debug_str 00000000 .LASF30
00000249 l .debug_str 00000000 .LASF31
00000026 l .debug_str 00000000 .LASF32
00000057 l .debug_str 00000000 .LASF33
0000000e l .debug_str 00000000 .LASF34
00000294 l .debug_str 00000000 .LASF35
000002cb l .debug_str 00000000 .LASF36
00000038 l .debug_str 00000000 .LASF37
000000ff l .debug_str 00000000 .LASF43
00000136 l .debug_str 00000000 .LASF44
0000013f l .debug_str 00000000 .LASF38
00000145 l .debug_str 00000000 .LASF39
0000002c l .debug_str 00000000 .LASF45
00000000 l d .comment 00000000 .comment
00000000 g .text 00000120 .hidden ___divsf3
00000000 *UND* 00000000 ___unpack_f
00000000 *UND* 00000000 ___thenan_sf
00000000 *UND* 00000000 ___pack_f
Disassembly of section .text:
00000000 <___divsf3>:
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
0: 975c 0701 str r4,[sp],-0xe
FLO_union_type au, bu;
au.value = arg_a;
bu.value = arg_b;
unpack_d (&au, &a);
4: 800b 0002 mov r4,0x0
4: R_EPIPHANY_LOW ___unpack_f
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
8: d6dc 2401 str lr,[sp,+0xd]
fp_number_type a;
fp_number_type b;
const fp_number_type *res;
FLO_union_type au, bu;
au.value = arg_a;
c: 155c 0400 str r0,[sp,+0x2]
bu.value = arg_b;
10: 35dc 0400 str r1,[sp,+0x3]
unpack_d (&au, &a);
14: 141b 0401 add r0,sp,8
18: 341b 0402 add r1,sp,16
1c: 800b 1002 movt r4,0x0
1c: R_EPIPHANY_HIGH ___unpack_f
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
20: 77dc 2401 str fp,[sp,+0xf]
FLO_union_type au, bu;
au.value = arg_a;
bu.value = arg_b;
unpack_d (&au, &a);
24: 1152 jalr r4
unpack_d (&bu, &b);
26: 341b 0404 add r1,sp,32
2a: 161b 0401 add r0,sp,12
2e: 1152 jalr r4
30: 364c 0400 ldr r1,[sp,+0x4]
fractype bit;
fractype numerator;
fractype denominator;
fractype quotient;
if (isnan (a))
34: 04b3 sub r0,r1,1
36: 5b40 blteu ec <___divsf3+0xec>
38: 144c 0401 ldr r0,[sp,+0x8]
{
return a;
}
if (isnan (b))
3c: 40b3 sub r2,r0,1
3e: 5a40 blteu f2 <___divsf3+0xf2>
{
return b;
}
a->sign = a->sign ^ b->sign;
40: 76cc 0400 ldr r3,[sp,+0x5]
44: 54cc 0401 ldr r2,[sp,+0x9]
48: 4d0a eor r2,r3,r2
4a: 56dc 0400 str r2,[sp,+0x5]
if (isinf (a) || iszero (a))
4e: 663b 0000 sub r3,r1,4
52: 0400 beq 5a <___divsf3+0x5a>
54: 053b 4000 sub r16,r1,2
58: 0410 bne 60 <___divsf3+0x60>
{
if (a->class == b->class)
5a: 443a sub r2,r1,r0
5c: 4810 bne ec <___divsf3+0xec>
5e: 4ee0 b fa <___divsf3+0xfa>
return makenan ();
return a;
}
if (isinf (b))
60: 623b 0000 sub r3,r0,4
64: 0710 bne 72 <___divsf3+0x72>
{
a->fraction.ll = 0;
66: 0003 mov r0,0x0
68: 17dc 0400 str r0,[sp,+0x7]
a->normal_exp = 0;
6c: 175c 0400 str r0,[sp,+0x6]
70: 07e0 b 7e <___divsf3+0x7e>
return a;
}
if (iszero (b))
72: 013b 4000 sub r16,r0,2
76: 0610 bne 82 <___divsf3+0x82>
{
a->class = CLASS_INFINITY;
78: 0083 mov r0,0x4
7a: 165c 0400 str r0,[sp,+0x4]
return a;
7e: 0203 mov r0,0x10
80: 3ae0 b f4 <___divsf3+0xf4>
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
82: 154c 0401 ldr r0,[sp,+0xa]
86: 374c 0400 ldr r1,[sp,+0x6]
numerator = a->fraction.ll;
denominator = b->fraction.ll;
8a: 95cc 2401 ldr r12,[sp,+0xb]
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
8e: 243a sub r1,r1,r0
numerator = a->fraction.ll;
90: 17cc 0400 ldr r0,[sp,+0x7]
{
/* quotient =
( numerator / denominator) * 2^(numerator exponent - denominator exponent)
*/
a->normal_exp = a->normal_exp - b->normal_exp;
94: 375c 0400 str r1,[sp,+0x6]
numerator = a->fraction.ll;
denominator = b->fraction.ll;
if (numerator < denominator)
98: 423f 008a sub r2,r0,r12
9c: 0530 bgteu a6 <___divsf3+0xa6>
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a->normal_exp--;
9e: 2793 add r1,r1,-1
denominator = b->fraction.ll;
if (numerator < denominator)
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a0: 0036 lsl r0,r0,0x1
a->normal_exp--;
a2: 375c 0400 str r1,[sp,+0x6]
}
bit = IMPLICIT_1;
a6: 600b 0002 mov r3,0x0
}
}
FLO_type
divide (FLO_type arg_a, FLO_type arg_b)
{
aa: 43e3 mov r2,0x1f
{
/* Fraction will be less than 1.0 */
numerator *= 2;
a->normal_exp--;
}
bit = IMPLICIT_1;
ac: 600b 1402 movt r3,0x4000
quotient = 0;
b0: 2003 mov r1,0x0
/* ??? Does divide one bit at a time. Optimize. */
while (bit)
{
if (numerator >= denominator)
b2: 023f 408a sub r16,r0,r12
b6: 0450 bltu be <___divsf3+0xbe>
{
quotient |= bit;
b8: 25fa orr r1,r1,r3
numerator -= denominator;
ba: 023f 008a sub r0,r0,r12
}
bit >>= 1;
be: 6c26 lsr r3,r3,0x1
numerator *= 2;
c0: 0036 lsl r0,r0,0x1
a->normal_exp--;
}
bit = IMPLICIT_1;
quotient = 0;
/* ??? Does divide one bit at a time. Optimize. */
while (bit)
c2: 48b3 sub r2,r2,1
c4: f710 bne b2 <___divsf3+0xb2>
}
bit >>= 1;
numerator *= 2;
}
if (!ROUND_TOWARDS_ZERO && (quotient & GARDMASK) == GARDMSB)
c6: 4fe3 mov r2,0x7f
c8: 455a and r2,r1,r2
ca: 683b 0008 sub r3,r2,64
ce: 0d10 bne e8 <___divsf3+0xe8>
{
if (quotient & (1 << NGARDS))
d0: 071f 4006 lsl r16,r1,0x18
d4: 0a80 blt e8 <___divsf3+0xe8>
/* Because we re half way, we would round to even by adding
GARDROUND + 1, except that s also done in the packing
function, and rounding twice will lose precision and cause
the result to be too far off. */
}
else if (numerator)
d6: 4033 sub r2,r0,0
d8: 0800 beq e8 <___divsf3+0xe8>
that, we round here and not in pack_d, because there we
dont have numerator available anymore. */
quotient += GARDROUND + 1;
/* Avoid further rounding in pack_d. */
quotient &= ~(fractype) GARDMASK;
da: 100b 0ff2 mov r0,0xff80
{
/* Were a further than half way by the small amount
corresponding to the bits set in "numerator". Knowing
that, we round here and not in pack_d, because there we
dont have "numerator" available anymore. */
quotient += GARDROUND + 1;
de: 241b 0008 add r1,r1,64
/* Avoid further rounding in pack_d. */
quotient &= ~(fractype) GARDMASK;
e2: 1feb 1ff2 movt r0,0xffff
e6: 245a and r1,r1,r0
}
}
a->fraction.ll = quotient;
e8: 37dc 0400 str r1,[sp,+0x7]
return (a);
ec: 141b 0402 add r0,sp,16
f0: 09e0 b 102 <___divsf3+0x102>
{
return a;
}
if (isnan (b))
{
return b;
f2: 0403 mov r0,0x20
f4: 029f 008a add r0,r0,sp
f8: 05e0 b 102 <___divsf3+0x102>
a->sign = a->sign ^ b->sign;
if (isinf (a) || iszero (a))
{
if (a->class == b->class)
return makenan ();
fa: 000b 0002 mov r0,0x0
fa: R_EPIPHANY_LOW ___thenan_sf
fe: 000b 1002 movt r0,0x0
fe: R_EPIPHANY_HIGH ___thenan_sf
unpack_d (&au, &a);
unpack_d (&bu, &b);
res = _fpdiv_parts (&a, &b);
return pack_d (res);
102: 200b 0002 mov r1,0x0
102: R_EPIPHANY_LOW ___pack_f
106: 200b 1002 movt r1,0x0
106: R_EPIPHANY_HIGH ___pack_f
10a: 0552 jalr r1
}
10c: 77cc 2401 ldr fp,[sp,+0xf]
110: 974c 0401 ldr r4,[sp,+0xe]
114: d6cc 2401 ldr lr,[sp,+0xd]
118: b41b 2407 add sp,sp,56
11c: 194f 0402 rts
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment