1/* Copyright (C) 2006-2021 Free Software Foundation, Inc. 2 Contributor: Joern Rennecke <joern.rennecke@embecosm.com> 3 on behalf of Synopsys Inc. 4 5This file is part of GCC. 6 7GCC is free software; you can redistribute it and/or modify it under 8the terms of the GNU General Public License as published by the Free 9Software Foundation; either version 3, or (at your option) any later 10version. 11 12GCC is distributed in the hope that it will be useful, but WITHOUT ANY 13WARRANTY; without even the implied warranty of MERCHANTABILITY or 14FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 15for more details. 16 17Under Section 7 of GPL version 3, you are granted additional 18permissions described in the GCC Runtime Library Exception, version 193.1, as published by the Free Software Foundation. 20 21You should have received a copy of the GNU General Public License and 22a copy of the GCC Runtime Library Exception along with this program; 23see the files COPYING3 and COPYING.RUNTIME respectively. If not, see 24<http://www.gnu.org/licenses/>. */ 25 26#include "arc-ieee-754.h" 27 28#if 0 /* DEBUG */ 29 FUNC(__truncdfsf2) 30 .global __truncdfsf2 31 .balign 4 32__truncdfsf2: 33 push_s blink 34 push_s r0 35 bl.d __truncdfsf2_c 36 push_s r1 37 mov_s r2,r0 38 pop_s r1 39 ld r0,[sp] 40 bl.d __truncdfsf2_asm 41 st r2,[sp] 42 pop_s r1 43 pop_s blink 44 cmp r0,r1 45 jeq_s [blink] 46 and r12,r0,r1 47 bic.f 0,0x7f800000,r12 48 bne 0f 49 bmsk.f 0,r0,22 50 bmsk.ne.f r1,r1,22 51 jne_s [blink] ; both NaN -> OK 520: bl abort 53 ENDFUNC(__truncdfsf2) 54#define __truncdfsf2 __truncdfsf2_asm 55#endif /* DEBUG */ 56 57 .global __truncdfsf2 58 .balign 4 59 FUNC(__truncdfsf2) 60__truncdfsf2: 61 lsr r2,DBL0H,20 62 asl_s DBL0H,DBL0H,12 63 sub r12,r2,0x380 64 bclr.f r3,r12,11 65 brhs r3,0xff,.Lill_exp 66 beq_l .Ldenorm0 67 asl_s r12,r12,23 68 tst DBL0L, \ 69 0x2fffffff /* Check if msb guard bit wants rounding up. */ 70 lsr_s DBL0L,DBL0L,28 71 lsr_s DBL0H,DBL0H,8 72 add.ne DBL0L,DBL0L,1 73 add_s DBL0H,DBL0H,DBL0L 74 lsr_s DBL0H,DBL0H 75 btst_s r2,11 76 add_s r0,DBL0H,r12 77 j_s.d [blink] 78 bxor.ne r0,r0,31 79 .balign 4 80.Lill_exp: 81 bbit1 r2,10,.Linf_nan 82 bmsk_s r12,r12,9 83 rsub.f r12,r12,8+0x400-32 ; Go from 9 to 1 guard bit in MSW. */ 84 bhs_s .Lzero 85 lsr r3,DBL0L,21 86 rrc DBL0H,DBL0H ; insert leading 1 87 asl.f 0,DBL0L,8 ; check lower 24 guard bits 88 add_s r3,DBL0H,r3 89 add.pnz r3,r3,1 ; assemble fraction with compressed guard bits. 90 lsr r0,r3,r12 91 neg_s r12,r12 92 btst_s r0,1 93 asl.eq.f r3,r3,r12 94 add.ne r0,r0,1 95 btst_s r2,11 96 lsr_s r0,r0 97 j_s.d [blink] 98 bxor.ne r0,r0,31 99.Lzero: 100 lsr_s r2,r2,11 101 j_s.d [blink] 102 asl r0,r2,31 103.Ldenorm0: 104 asl_s r12,r12,20 105 tst DBL0L, \ 106 0x5fffffff /* Check if msb guard bit wants rounding up. */ 107 lsr_s DBL0L,DBL0L,29 108 lsr_s DBL0H,DBL0H,9 109 add.ne DBL0L,DBL0L,1 110 bset_s DBL0H,DBL0H,23 111 add_s DBL0H,DBL0H,DBL0L 112 lsr_s DBL0H,DBL0H 113 j_s.d [blink] 114 add_l r0,DBL0H,r12 115 116/* We would generally say that NaNs must have a non-zero high fraction part, 117 but to allow hardware double precision floating point to interoperate 118 with single precision software floating point, we make an exception here. 119 The cost is to replace a tst_s DBL0H with an or.f DBL0L,DBL0L,DBL0H . 120 As we start out unaligned, and there is an odd number of other short insns, 121 we have a choice of letting this cost us a misalign penalty or 122 4 more bytes (if we align the code). We choose the former here because 123 infinity / NaN is not expected to be prevalent in time-critical code. */ 124.Linf_nan: 125 or.f DBL0L,DBL0L,DBL0H 126 mov_s r0,1 127 add.ne r2,r2,1 128 tst r2,0x7ff 129 asl.ne r0,r0,23 130 btst_s r12,11 131 neg r0,r0 132 j_s.d [blink] 133 bxor.eq r0,r0,31 134 ENDFUNC(__truncdfsf2) 135