First public contribution.
2 * LIBOIL - Library of Optimized Inner Loops
3 * Copyright (c) 2003,2004 David A. Schleef <ds@schleef.org>
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
15 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
16 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
17 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
18 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT,
19 * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
20 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
21 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
22 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
23 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
24 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
25 * POSSIBILITY OF SUCH DAMAGE.
27 //Portions Copyright (c) 2008-2009 Nokia Corporation and/or its subsidiary(-ies). All rights reserved.
32 #include <liboil/liboilfunction.h>
39 static void conv_f32_u8_bitstuff(float *dst, int dest_stride, const uint8_t *src,
40 int src_stride, int n)
42 const float offset = -65536;
43 union ieee754_float id;
48 id.ieee.mantissa = (*src<<7);
50 OIL_INCREMENT(dst, dest_stride);
51 OIL_INCREMENT(src, src_stride);
54 OIL_DEFINE_IMPL(conv_f32_u8_bitstuff, conv_f32_u8);
56 static void conv_f32_s8_bitstuff(float *dst, int dest_stride, const int8_t *src,
57 int src_stride, int n)
59 const float offset = -384;
60 union ieee754_float id;
65 id.ieee.mantissa = ((*src^0x80)<<15);
67 OIL_INCREMENT(dst, dest_stride);
68 OIL_INCREMENT(src, src_stride);
71 OIL_DEFINE_IMPL(conv_f32_s8_bitstuff, conv_f32_s8);
73 static void conv_f32_u16_bitstuff(float *dst, int dest_stride, const uint16_t *src,
74 int src_stride, int n)
76 const float offset = -65536;
77 union ieee754_float id;
82 id.ieee.mantissa = (*src<<7);
84 OIL_INCREMENT(dst, dest_stride);
85 OIL_INCREMENT(src, src_stride);
88 OIL_DEFINE_IMPL(conv_f32_u16_bitstuff, conv_f32_u16);
90 #ifdef ENABLE_BROKEN_IMPLS
91 /* This is intermittently broken on powerpc for unknown reasons */
92 static void conv_f32_s16_bitstuff(float *dst, int dest_stride, const int16_t *src,
93 int src_stride, int n)
95 const float offset = -98304;
96 union ieee754_float id;
101 id.ieee.mantissa = ((*src^0x8000)<<7);
102 *dst = id.f + offset;
103 OIL_INCREMENT(dst, dest_stride);
104 OIL_INCREMENT(src, src_stride);
107 OIL_DEFINE_IMPL(conv_f32_s16_bitstuff, conv_f32_s16);
111 #define signbit_S32(x) (((uint32_t)(x))>>31)
115 /* This implementation is slightly inaccurate */
116 static void conv_s16_f32_bitstuff(int16_t *dst, int dest_stride, const float *src,
117 int src_stride, int n)
119 const float offset = 98304.5;
120 union ieee754_double id;
125 id.d = offset + *src;
126 d = 0x8000 | (id.ieee.mantissa0 >> 4);
127 d += (-32768-d)*signbit_S32(id.ieee.exponent-1039);
128 d += (32767-d)*signbit_S32(1039-id.ieee.exponent);
130 OIL_INCREMENT(dst, dest_stride);
131 OIL_INCREMENT(src, src_stride);
134 OIL_DEFINE_IMPL(conv_s16_f32_bitstuff, conv_s16_f32);
139 static void conv_f64_u8_bitstuff(float *dst, int dest_stride, const uint8_t *src,
140 int src_stride, int n)
142 const float offset = -65536;
143 union ieee754_float id;
148 id.ieee.mantissa = (*src<<7);
149 *dst = id.f + offset;
150 OIL_INCREMENT(dst, dest_stride);
151 OIL_INCREMENT(src, src_stride);
154 OIL_DEFINE_IMPL(conv_f64_u8_bitstuff, conv_f64_u8);
156 static void conv_f64_s8_bitstuff(float *dst, int dest_stride, const int8_t *src,
157 int src_stride, int n)
159 const float offset = -384;
160 union ieee754_float id;
165 id.ieee.mantissa = ((*src^0x80)<<15);
166 *dst = id.f + offset;
167 OIL_INCREMENT(dst, dest_stride);
168 OIL_INCREMENT(src, src_stride);
171 OIL_DEFINE_IMPL(conv_f64_s8_bitstuff, conv_f64_s8);
173 static void conv_f64_u16_bitstuff(float *dst, int dest_stride, const uint16_t *src,
174 int src_stride, int n)
176 const float offset = -65536;
177 union ieee754_float id;
182 id.ieee.mantissa = (*src<<7);
183 *dst = id.f + offset;
184 OIL_INCREMENT(dst, dest_stride);
185 OIL_INCREMENT(src, src_stride);
188 OIL_DEFINE_IMPL(conv_f64_u16_bitstuff, conv_f64_u16);
190 static void conv_f64_s16_bitstuff(float *dst, int dest_stride, const int16_t *src,
191 int src_stride, int n)
193 const float offset = -98304;
194 union ieee754_float id;
199 id.ieee.mantissa = ((*src^0x8000)<<7);
200 *dst = id.f + offset;
201 OIL_INCREMENT(dst, dest_stride);
202 OIL_INCREMENT(src, src_stride);
205 OIL_DEFINE_IMPL(conv_f64_s16_bitstuff, conv_f64_s16);
210 /* This implementation is slightly inaccurate */
211 static void conv_s16_f64_bitstuff(int16_t *dst, int dest_stride, const float *src,
212 int src_stride, int n)
214 const float offset = 98304.5;
215 union ieee754_double id;
220 id.d = offset + *src;
221 d = 0x8000 ^ (id.ieee.mantissa0 >> 4);
222 d += (-32768-d)*signbit_S32(id.ieee.exponent-1039);
223 d += (32767-d)*signbit_S32(1039-id.ieee.exponent);
226 if (id.ieee.exponent < 1039) {
229 if (id.ieee.exponent > 1039) {
234 OIL_INCREMENT (dst, dest_stride);
235 OIL_INCREMENT (src, src_stride);
238 OIL_DEFINE_IMPL(conv_s16_f64_bitstuff, conv_s16_f64);
247 OilFunctionImpl* __oil_function_impl_conv_f32_u8_bitstuff() {
248 return &_oil_function_impl_conv_f32_u8_bitstuff;
254 OilFunctionImpl* __oil_function_impl_conv_f32_s8_bitstuff() {
255 return &_oil_function_impl_conv_f32_s8_bitstuff;
261 OilFunctionImpl* __oil_function_impl_conv_f32_u16_bitstuff() {
262 return &_oil_function_impl_conv_f32_u16_bitstuff;
268 OilFunctionImpl* __oil_function_impl_conv_f32_s16_bitstuff() {
269 return &_oil_function_impl_conv_f32_s16_bitstuff;
275 OilFunctionImpl* __oil_function_impl_conv_s16_f32_bitstuff() {
276 return &_oil_function_impl_conv_s16_f32_bitstuff;
282 OilFunctionImpl* __oil_function_impl_conv_f64_u8_bitstuff() {
283 return &_oil_function_impl_conv_f64_u8_bitstuff;
289 OilFunctionImpl* __oil_function_impl_conv_f64_s8_bitstuff() {
290 return &_oil_function_impl_conv_f64_s8_bitstuff;
296 OilFunctionImpl* __oil_function_impl_conv_f64_u16_bitstuff() {
297 return &_oil_function_impl_conv_f64_u16_bitstuff;
303 OilFunctionImpl* __oil_function_impl_conv_f64_s16_bitstuff() {
304 return &_oil_function_impl_conv_f64_s16_bitstuff;
310 OilFunctionImpl* __oil_function_impl_conv_s16_f64_bitstuff() {
311 return &_oil_function_impl_conv_s16_f64_bitstuff;