1/* 2 * Copyright (c) 2013-2014, NVIDIA Corporation. All rights reserved. 3 * Johnny Qiu <joqiu@nvidia.com> 4 * Shu Zhang <chazhang@nvidia.com> 5 * 6 * Redistribution and use in source and binary forms, with or without 7 * modification, are permitted provided that the following conditions are 8 * met: 9 * * Redistributions of source code must retain the above copyright 10 * notice, this list of conditions and the following disclaimer. 11 * * Redistributions in binary form must reproduce the above 12 * copyright notice, this list of conditions and the following 13 * disclaimer in the documentation and/or other materials provided 14 * with the distribution. 15 * * Neither the name of The Linux Foundation nor the names of its 16 * contributors may be used to endorse or promote products derived 17 * from this software without specific prior written permission. 18 * 19 * THIS SOFTWARE IS PROVIDED "AS IS" AND ANY EXPRESS OR IMPLIED 20 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 21 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT 22 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS 23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR 26 * BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, 27 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE 28 * OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN 29 * IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 30 */ 31 32#include <float.h> 33#include <private/bionic_asm.h> 34 35ENTRY(floor) /* x in r0, r1 */ 36 37 and r3, r1, #0x80000000 /* sign(x) */ 38 bic r1, r1, #0x80000000 /* x = abs(x) */ 39 40 /* extract exp of x */ 41 lsr r2, r1, #20 42 sub r2, r2, #0x3fc 43 subs r2, r2, #0x3 /* r2 <- exp */ 44 45 /* |x| < 1.0? */ 46 blt .Lx_lt_one 47 48 /* x < 0? */ 49 cmp r3, #0 50 bne .Lclr_frac_neg 51 52 /* |x| <= 2^20? */ 53 cmp r2, #20 54 ble .Lclr_frac_r1 55 56 /* |x| < 2^52? */ 57 cmp r2, #52 58 blt .Lclr_frac_r0 59 60 /* return x */ 61 bx lr 62 63.Lclr_frac_r1: 64 rsb r2, r2, #20 65 lsr r1, r1, r2 66 lsl r1, r1, r2 67 mov r0, #0 68 bx lr 69 70.Lclr_frac_r0: 71 rsb r2, r2, #52 72 lsr r0, r0, r2 73 lsl r0, r0, r2 74 bx lr 75 76.Lclr_frac_neg: 77 /* |x| <= 2^20? */ 78 cmp r2, #20 79 ble .Lclr_frac_r1_neg 80 81 /* |x| < 2^52? */ 82 cmp r2, #52 83 blt .Lclr_frac_r0_neg 84 85 /* return x */ 86 orr r1, r1, #0x80000000 87 bx lr 88 89.Lclr_frac_r1_neg: 90 rsb r2, r2, #20 91 mov r3, #1 92 lsl r3, r3, r2 93 sub r3, r3, #1 94 and r3, r1, r3 95 orr r3, r3, r0 96 lsr r1, r1, r2 97 lsl r1, r1, r2 98 mov r0, #0 99 b .Lreturn_x_neg 100 101.Lclr_frac_r0_neg: 102 rsb r2, r2, #52 103 mov r3, #1 104 lsl r3, r3, r2 105 sub r3, r3, #1 106 and r3, r0, r3 107 lsr r0, r0, r2 108 lsl r0, r0, r2 109 b .Lreturn_x_neg 110 111.Lx_lt_one: 112 /* x == +-0? */ 113 cmp r0, #0 114 cmpeq r1, #0 115 orreq r1, r1, r3 116 bxeq lr 117 118 /* (x > 0) ? 0 : -1 */ 119 mov r1, #0x00100000 120 mov r0, #0 121 cmp r3, #0 122 movne r1, #0xc0000000 123 sub r1, r1, #0x00100000 124 bx lr 125 126.Lreturn_x_neg: 127 cmp r3, #0 128 orr r1, r1, #0x80000000 129 bxeq lr 130 131 vmov d16, r0, r1 132 vmov.f64 d18, #1.0 133 vsub.f64 d16, d16, d18 134 vmov r0, r1, d16 135 bx lr 136 137END(floor) 138 139ALIAS_SYMBOL(floorl, floor); 140