cosmopolitan/third_party/compiler_rt/floatunsisf.c
Justine Tunney 7e0a09feec
Mint APE Loader v1.5
This change ports APE Loader to Linux AARCH64, so that Raspberry Pi
users can run programs like redbean, without the executable needing
to modify itself. Progress has also slipped into this change on the
issue of making progress better conforming to user expectations and
industry standards regarding which symbols we're allowed to declare
2023-07-26 13:54:49 -07:00

61 lines
1.9 KiB
C

/* clang-format off */
//===-- lib/floatunsisf.c - uint -> single-precision conversion ---*- C -*-===//
//
// The LLVM Compiler Infrastructure
//
// This file is dual licensed under the MIT and the University of Illinois Open
// Source Licenses. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// This file implements unsigned integer to single-precision conversion for the
// compiler-rt library in the IEEE-754 default round-to-nearest, ties-to-even
// mode.
//
//===----------------------------------------------------------------------===//
__static_yoink("huge_compiler_rt_license");
#define SINGLE_PRECISION
#include "third_party/compiler_rt/fp_lib.inc"
#include "third_party/compiler_rt/int_lib.h"
COMPILER_RT_ABI fp_t
__floatunsisf(unsigned int a) {
const int aWidth = sizeof a * CHAR_BIT;
// Handle zero as a special case to protect clz
if (a == 0) return fromRep(0);
// Exponent of (fp_t)a is the width of abs(a).
const int exponent = (aWidth - 1) - __builtin_clz(a);
rep_t result;
// Shift a into the significand field, rounding if it is a right-shift
if (exponent <= significandBits) {
const int shift = significandBits - exponent;
result = (rep_t)a << shift ^ implicitBit;
} else {
const int shift = exponent - significandBits;
result = (rep_t)a >> shift ^ implicitBit;
rep_t round = (rep_t)a << (typeWidth - shift);
if (round > signBit) result++;
if (round == signBit) result += result & 1;
}
// Insert the exponent
result += (rep_t)(exponent + exponentBias) << significandBits;
return fromRep(result);
}
#if defined(__ARM_EABI__)
#if defined(COMPILER_RT_ARMHF_TARGET)
AEABI_RTABI fp_t __aeabi_ui2f(unsigned int a) {
return __floatunsisf(a);
}
#else
AEABI_RTABI fp_t __aeabi_ui2f(unsigned int a) COMPILER_RT_ALIAS(__floatunsisf);
#endif
#endif