1c55a96383497a772a307b346368133960b02ad03Eric Laurent/* 2c55a96383497a772a307b346368133960b02ad03Eric Laurent * Copyright (c) 2011 The WebRTC project authors. All Rights Reserved. 3c55a96383497a772a307b346368133960b02ad03Eric Laurent * 4c55a96383497a772a307b346368133960b02ad03Eric Laurent * Use of this source code is governed by a BSD-style license 5c55a96383497a772a307b346368133960b02ad03Eric Laurent * that can be found in the LICENSE file in the root of the source 6c55a96383497a772a307b346368133960b02ad03Eric Laurent * tree. An additional intellectual property rights grant can be found 7c55a96383497a772a307b346368133960b02ad03Eric Laurent * in the file PATENTS. All contributing project authors may 8c55a96383497a772a307b346368133960b02ad03Eric Laurent * be found in the AUTHORS file in the root of the source tree. 9c55a96383497a772a307b346368133960b02ad03Eric Laurent */ 10c55a96383497a772a307b346368133960b02ad03Eric Laurent 11c55a96383497a772a307b346368133960b02ad03Eric Laurent 12c55a96383497a772a307b346368133960b02ad03Eric Laurent// This header file includes the inline functions in 13c55a96383497a772a307b346368133960b02ad03Eric Laurent// the fix point signal processing library. 14c55a96383497a772a307b346368133960b02ad03Eric Laurent 15c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifndef WEBRTC_SPL_SPL_INL_H_ 16c55a96383497a772a307b346368133960b02ad03Eric Laurent#define WEBRTC_SPL_SPL_INL_H_ 17c55a96383497a772a307b346368133960b02ad03Eric Laurent 18c55a96383497a772a307b346368133960b02ad03Eric Laurent#ifdef WEBRTC_ARCH_ARM_V7A 19c55a96383497a772a307b346368133960b02ad03Eric Laurent#include "spl_inl_armv7.h" 20c55a96383497a772a307b346368133960b02ad03Eric Laurent#else 21c55a96383497a772a307b346368133960b02ad03Eric Laurent 22c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline WebRtc_Word16 WebRtcSpl_SatW32ToW16(WebRtc_Word32 value32) { 23c55a96383497a772a307b346368133960b02ad03Eric Laurent WebRtc_Word16 out16 = (WebRtc_Word16) value32; 24c55a96383497a772a307b346368133960b02ad03Eric Laurent 25c55a96383497a772a307b346368133960b02ad03Eric Laurent if (value32 > 32767) 26c55a96383497a772a307b346368133960b02ad03Eric Laurent out16 = 32767; 27c55a96383497a772a307b346368133960b02ad03Eric Laurent else if (value32 < -32768) 28c55a96383497a772a307b346368133960b02ad03Eric Laurent out16 = -32768; 29c55a96383497a772a307b346368133960b02ad03Eric Laurent 30c55a96383497a772a307b346368133960b02ad03Eric Laurent return out16; 31c55a96383497a772a307b346368133960b02ad03Eric Laurent} 32c55a96383497a772a307b346368133960b02ad03Eric Laurent 33c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline WebRtc_Word16 WebRtcSpl_AddSatW16(WebRtc_Word16 a, 34c55a96383497a772a307b346368133960b02ad03Eric Laurent WebRtc_Word16 b) { 35c55a96383497a772a307b346368133960b02ad03Eric Laurent return WebRtcSpl_SatW32ToW16((WebRtc_Word32) a + (WebRtc_Word32) b); 36c55a96383497a772a307b346368133960b02ad03Eric Laurent} 37c55a96383497a772a307b346368133960b02ad03Eric Laurent 38c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline WebRtc_Word32 WebRtcSpl_AddSatW32(WebRtc_Word32 l_var1, 39c55a96383497a772a307b346368133960b02ad03Eric Laurent WebRtc_Word32 l_var2) { 40c55a96383497a772a307b346368133960b02ad03Eric Laurent WebRtc_Word32 l_sum; 41c55a96383497a772a307b346368133960b02ad03Eric Laurent 42c55a96383497a772a307b346368133960b02ad03Eric Laurent // perform long addition 43c55a96383497a772a307b346368133960b02ad03Eric Laurent l_sum = l_var1 + l_var2; 44c55a96383497a772a307b346368133960b02ad03Eric Laurent 45c55a96383497a772a307b346368133960b02ad03Eric Laurent // check for under or overflow 46c55a96383497a772a307b346368133960b02ad03Eric Laurent if (WEBRTC_SPL_IS_NEG(l_var1)) { 47c55a96383497a772a307b346368133960b02ad03Eric Laurent if (WEBRTC_SPL_IS_NEG(l_var2) && !WEBRTC_SPL_IS_NEG(l_sum)) { 48c55a96383497a772a307b346368133960b02ad03Eric Laurent l_sum = (WebRtc_Word32)0x80000000; 49c55a96383497a772a307b346368133960b02ad03Eric Laurent } 50c55a96383497a772a307b346368133960b02ad03Eric Laurent } else { 51c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!WEBRTC_SPL_IS_NEG(l_var2) && WEBRTC_SPL_IS_NEG(l_sum)) { 52c55a96383497a772a307b346368133960b02ad03Eric Laurent l_sum = (WebRtc_Word32)0x7FFFFFFF; 53c55a96383497a772a307b346368133960b02ad03Eric Laurent } 54c55a96383497a772a307b346368133960b02ad03Eric Laurent } 55c55a96383497a772a307b346368133960b02ad03Eric Laurent 56c55a96383497a772a307b346368133960b02ad03Eric Laurent return l_sum; 57c55a96383497a772a307b346368133960b02ad03Eric Laurent} 58c55a96383497a772a307b346368133960b02ad03Eric Laurent 59c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline WebRtc_Word16 WebRtcSpl_SubSatW16(WebRtc_Word16 var1, 60c55a96383497a772a307b346368133960b02ad03Eric Laurent WebRtc_Word16 var2) { 61c55a96383497a772a307b346368133960b02ad03Eric Laurent return WebRtcSpl_SatW32ToW16((WebRtc_Word32) var1 - (WebRtc_Word32) var2); 62c55a96383497a772a307b346368133960b02ad03Eric Laurent} 63c55a96383497a772a307b346368133960b02ad03Eric Laurent 64c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline WebRtc_Word32 WebRtcSpl_SubSatW32(WebRtc_Word32 l_var1, 65c55a96383497a772a307b346368133960b02ad03Eric Laurent WebRtc_Word32 l_var2) { 66c55a96383497a772a307b346368133960b02ad03Eric Laurent WebRtc_Word32 l_diff; 67c55a96383497a772a307b346368133960b02ad03Eric Laurent 68c55a96383497a772a307b346368133960b02ad03Eric Laurent // perform subtraction 69c55a96383497a772a307b346368133960b02ad03Eric Laurent l_diff = l_var1 - l_var2; 70c55a96383497a772a307b346368133960b02ad03Eric Laurent 71c55a96383497a772a307b346368133960b02ad03Eric Laurent // check for underflow 72c55a96383497a772a307b346368133960b02ad03Eric Laurent if ((l_var1 < 0) && (l_var2 > 0) && (l_diff > 0)) 73c55a96383497a772a307b346368133960b02ad03Eric Laurent l_diff = (WebRtc_Word32)0x80000000; 74c55a96383497a772a307b346368133960b02ad03Eric Laurent // check for overflow 75c55a96383497a772a307b346368133960b02ad03Eric Laurent if ((l_var1 > 0) && (l_var2 < 0) && (l_diff < 0)) 76c55a96383497a772a307b346368133960b02ad03Eric Laurent l_diff = (WebRtc_Word32)0x7FFFFFFF; 77c55a96383497a772a307b346368133960b02ad03Eric Laurent 78c55a96383497a772a307b346368133960b02ad03Eric Laurent return l_diff; 79c55a96383497a772a307b346368133960b02ad03Eric Laurent} 80c55a96383497a772a307b346368133960b02ad03Eric Laurent 81c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline WebRtc_Word16 WebRtcSpl_GetSizeInBits(WebRtc_UWord32 n) { 82c55a96383497a772a307b346368133960b02ad03Eric Laurent int bits; 83c55a96383497a772a307b346368133960b02ad03Eric Laurent 84c55a96383497a772a307b346368133960b02ad03Eric Laurent if (0xFFFF0000 & n) { 85c55a96383497a772a307b346368133960b02ad03Eric Laurent bits = 16; 86c55a96383497a772a307b346368133960b02ad03Eric Laurent } else { 87c55a96383497a772a307b346368133960b02ad03Eric Laurent bits = 0; 88c55a96383497a772a307b346368133960b02ad03Eric Laurent } 89c55a96383497a772a307b346368133960b02ad03Eric Laurent if (0x0000FF00 & (n >> bits)) bits += 8; 90c55a96383497a772a307b346368133960b02ad03Eric Laurent if (0x000000F0 & (n >> bits)) bits += 4; 91c55a96383497a772a307b346368133960b02ad03Eric Laurent if (0x0000000C & (n >> bits)) bits += 2; 92c55a96383497a772a307b346368133960b02ad03Eric Laurent if (0x00000002 & (n >> bits)) bits += 1; 93c55a96383497a772a307b346368133960b02ad03Eric Laurent if (0x00000001 & (n >> bits)) bits += 1; 94c55a96383497a772a307b346368133960b02ad03Eric Laurent 95c55a96383497a772a307b346368133960b02ad03Eric Laurent return bits; 96c55a96383497a772a307b346368133960b02ad03Eric Laurent} 97c55a96383497a772a307b346368133960b02ad03Eric Laurent 98c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline int WebRtcSpl_NormW32(WebRtc_Word32 a) { 99c55a96383497a772a307b346368133960b02ad03Eric Laurent int zeros; 100c55a96383497a772a307b346368133960b02ad03Eric Laurent 101c55a96383497a772a307b346368133960b02ad03Eric Laurent if (a <= 0) a ^= 0xFFFFFFFF; 102c55a96383497a772a307b346368133960b02ad03Eric Laurent 103c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xFFFF8000 & a)) { 104c55a96383497a772a307b346368133960b02ad03Eric Laurent zeros = 16; 105c55a96383497a772a307b346368133960b02ad03Eric Laurent } else { 106c55a96383497a772a307b346368133960b02ad03Eric Laurent zeros = 0; 107c55a96383497a772a307b346368133960b02ad03Eric Laurent } 108c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xFF800000 & (a << zeros))) zeros += 8; 109c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xF8000000 & (a << zeros))) zeros += 4; 110c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xE0000000 & (a << zeros))) zeros += 2; 111c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xC0000000 & (a << zeros))) zeros += 1; 112c55a96383497a772a307b346368133960b02ad03Eric Laurent 113c55a96383497a772a307b346368133960b02ad03Eric Laurent return zeros; 114c55a96383497a772a307b346368133960b02ad03Eric Laurent} 115c55a96383497a772a307b346368133960b02ad03Eric Laurent 116c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline int WebRtcSpl_NormU32(WebRtc_UWord32 a) { 117c55a96383497a772a307b346368133960b02ad03Eric Laurent int zeros; 118c55a96383497a772a307b346368133960b02ad03Eric Laurent 119c55a96383497a772a307b346368133960b02ad03Eric Laurent if (a == 0) return 0; 120c55a96383497a772a307b346368133960b02ad03Eric Laurent 121c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xFFFF0000 & a)) { 122c55a96383497a772a307b346368133960b02ad03Eric Laurent zeros = 16; 123c55a96383497a772a307b346368133960b02ad03Eric Laurent } else { 124c55a96383497a772a307b346368133960b02ad03Eric Laurent zeros = 0; 125c55a96383497a772a307b346368133960b02ad03Eric Laurent } 126c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xFF000000 & (a << zeros))) zeros += 8; 127c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xF0000000 & (a << zeros))) zeros += 4; 128c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xC0000000 & (a << zeros))) zeros += 2; 129c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0x80000000 & (a << zeros))) zeros += 1; 130c55a96383497a772a307b346368133960b02ad03Eric Laurent 131c55a96383497a772a307b346368133960b02ad03Eric Laurent return zeros; 132c55a96383497a772a307b346368133960b02ad03Eric Laurent} 133c55a96383497a772a307b346368133960b02ad03Eric Laurent 134c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline int WebRtcSpl_NormW16(WebRtc_Word16 a) { 135c55a96383497a772a307b346368133960b02ad03Eric Laurent int zeros; 136c55a96383497a772a307b346368133960b02ad03Eric Laurent 137c55a96383497a772a307b346368133960b02ad03Eric Laurent if (a <= 0) a ^= 0xFFFF; 138c55a96383497a772a307b346368133960b02ad03Eric Laurent 139c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xFF80 & a)) { 140c55a96383497a772a307b346368133960b02ad03Eric Laurent zeros = 8; 141c55a96383497a772a307b346368133960b02ad03Eric Laurent } else { 142c55a96383497a772a307b346368133960b02ad03Eric Laurent zeros = 0; 143c55a96383497a772a307b346368133960b02ad03Eric Laurent } 144c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xF800 & (a << zeros))) zeros += 4; 145c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xE000 & (a << zeros))) zeros += 2; 146c55a96383497a772a307b346368133960b02ad03Eric Laurent if (!(0xC000 & (a << zeros))) zeros += 1; 147c55a96383497a772a307b346368133960b02ad03Eric Laurent 148c55a96383497a772a307b346368133960b02ad03Eric Laurent return zeros; 149c55a96383497a772a307b346368133960b02ad03Eric Laurent} 150c55a96383497a772a307b346368133960b02ad03Eric Laurent 151c55a96383497a772a307b346368133960b02ad03Eric Laurentstatic __inline int32_t WebRtc_MulAccumW16(int16_t a, 152c55a96383497a772a307b346368133960b02ad03Eric Laurent int16_t b, 153c55a96383497a772a307b346368133960b02ad03Eric Laurent int32_t c) { 154c55a96383497a772a307b346368133960b02ad03Eric Laurent return (a * b + c); 155c55a96383497a772a307b346368133960b02ad03Eric Laurent} 156c55a96383497a772a307b346368133960b02ad03Eric Laurent 157c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif // WEBRTC_ARCH_ARM_V7A 158c55a96383497a772a307b346368133960b02ad03Eric Laurent 159c55a96383497a772a307b346368133960b02ad03Eric Laurent#endif // WEBRTC_SPL_SPL_INL_H_ 160