floatunsidf.c revision 0193b74976719b8aea4cb8874ba36b75836a8d6e
15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//===-- lib/floatunsidf.c - uint -> double-precision conversion ---*- C -*-===// 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The LLVM Compiler Infrastructure 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// This file is dual licensed under the MIT and the University of Illinois Open 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Source Licenses. See LICENSE.TXT for details. 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)//===----------------------------------------------------------------------===// 95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// 10f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// This file implements unsigned integer to double-precision conversion for the 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// compiler-rt library in the IEEE-754 default round-to-nearest, ties-to-even 127d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)// mode. 13868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)// 14f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)//===----------------------------------------------------------------------===// 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define DOUBLE_PRECISION 175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "fp_lib.h" 185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "int_lib.h" 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 21f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)ARM_EABI_FNALIAS(ui2d, floatunsidf) 22f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) 23f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)fp_t __floatunsidf(unsigned int a) { 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 25f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) const int aWidth = sizeof a * CHAR_BIT; 26f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) 27f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) // Handle zero as a special case to protect clz 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (a == 0) return fromRep(0); 29f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Exponent of (fp_t)a is the width of abs(a). 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const int exponent = (aWidth - 1) - __builtin_clz(a); 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) rep_t result; 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Shift a into the significand field and clear the implicit bit. 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const int shift = significandBits - exponent; 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = (rep_t)a << shift ^ implicitBit; 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 38f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles) // Insert the exponent 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result += (rep_t)(exponent + exponentBias) << significandBits; 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return fromRep(result); 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)