1135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent/* 2135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * Copyright (C) 2008 The Android Open Source Project 3135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * 4135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * Licensed under the Apache License, Version 2.0 (the "License"); 5135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * you may not use this file except in compliance with the License. 6135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * You may obtain a copy of the License at 7135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * 8135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * http://www.apache.org/licenses/LICENSE-2.0 9135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * 10135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * Unless required by applicable law or agreed to in writing, software 11135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * distributed under the License is distributed on an "AS IS" BASIS, 12135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * See the License for the specific language governing permissions and 14135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent * limitations under the License. 15135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent */ 16135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent#define LOG_TAG "EFFECTSMATH" 17135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent//#define LOG_NDEBUG 0 18135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent#include <cutils/log.h> 19135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent#include <assert.h> 20135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 21135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent#include "EffectsMath.h" 22135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 23135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent// gLogTab contains pre-calculated values of log2(1 + ai5*2^-1 + ai4*2^-2 + ai3*2^-3 + ai2*2^-4 + ai1*2^-5 + ai0*2^-6) 24135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent// for integers in the range 0 to 63 (i = ai5*2^5 + ai4*2^4 + ai3*2^3 + ai2*2^2 + ai1*2^1 + ai0*2^0) 25135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent// It is used for a better than piece wise approximation of lin to log2 conversion 26135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 27135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurentstatic const uint16_t gLogTab[] = 28135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent{ 29135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 0, 733, 1455, 2166, 30135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 2866, 3556, 4236, 4907, 31135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 5568, 6220, 6863, 7498, 32135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 8124, 8742, 9352, 9954, 33135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 10549, 11136, 11716, 12289, 34135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 12855, 13415, 13968, 14514, 35135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 15055, 15589, 16117, 16639, 36135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 17156, 17667, 18173, 18673, 37135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 19168, 19658, 20143, 20623, 38135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 21098, 21568, 22034, 22495, 39135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 22952, 23404, 23852, 24296, 40135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 24736, 25172, 25604, 26031, 41135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 26455, 26876, 27292, 27705, 42135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 28114, 28520, 28922, 29321, 43135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 29717, 30109, 30498, 30884, 44135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 31267, 31647, 32024, 32397, 45135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 32768 46135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent}; 47135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 48135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurentint32_t Effects_log2(uint32_t x) { 49135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t exp = 31 - __builtin_clz(x); 50135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent uint32_t segStart = x >> (exp - 6); 51135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent uint32_t i = segStart & 0x3F; 52135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t log = (int32_t)gLogTab[i]; 53135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t logEnd = (int32_t)gLogTab[i+1]; 54135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent segStart <<= exp - 6; 55135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 56135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent return (exp << 15) + log + (((x - segStart) * (logEnd - log)) >> (exp - 6)); 57135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent} 58135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 59135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent// gExpTab[i] = (2^(i>>6)) << 22 60135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurentstatic const uint32_t gExpTab[] = { 61135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 4194304, 4239977, 4286147, 4332820, 62135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 4380002, 4427697, 4475911, 4524651, 63135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 4573921, 4623728, 4674077, 4724974, 64135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 4776426, 4828438, 4881016, 4934167, 65135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 4987896, 5042211, 5097117, 5152621, 66135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 5208729, 5265449, 5322786, 5380747, 67135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 5439339, 5498570, 5558445, 5618973, 68135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 5680159, 5742012, 5804539, 5867746, 69135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 5931642, 5996233, 6061528, 6127533, 70135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 6194258, 6261709, 6329894, 6398822, 71135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 6468501, 6538938, 6610143, 6682122, 72135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 6754886, 6828442, 6902799, 6977965, 73135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 7053950, 7130763, 7208412, 7286906, 74135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 7366255, 7446469, 7527555, 7609525, 75135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 7692387, 7776152, 7860829, 7946428, 76135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 8032959, 8120432, 8208857, 8298246, 77135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 8388608 78135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent}; 79135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 80135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 81135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurentuint32_t Effects_exp2(int32_t x) { 82135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t i = x >> 15; 83135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent assert(i < 32); 84135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent x &= (1 << 15) - 1; 85135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t j = x >> 9; 86135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent x &= (1 << 9) - 1; 87135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent uint32_t exp = gExpTab[j]; 88135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent uint32_t expEnd = gExpTab[j+1]; 89135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 90135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent return ((exp << 9) + (expEnd - exp) * x) >> (31 - i); 91135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent} 92135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 93135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 94135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurentint16_t Effects_MillibelsToLinear16 (int32_t nGain) 95135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent{ 96135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent nGain = ((nGain + MB_TO_LIN_K1) << 15 ) / MB_TO_LIN_K2; 97135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent uint32_t exp2 = Effects_exp2(nGain); 98135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 99135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent if (exp2 > 32767) exp2 = 32767; 100135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 101135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent return (int16_t)exp2; 102135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent} 103135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 104135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 105135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurentint16_t Effects_Linear16ToMillibels (int32_t nGain) 106135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent{ 107135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent return (int16_t)(((MB_TO_LIN_K2*Effects_log2(nGain))>>15)-MB_TO_LIN_K1); 108135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent} 109135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 110135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 111135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurentint32_t Effects_Sqrt(int32_t in) 112135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent{ 113135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t tmp; 114135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t out = 0; 115135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t i; 116135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent int32_t j; 117135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 118135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 119135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent if (in == 0) return 0; 120135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 121135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent if (in >= 0x10000000) 122135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent { 123135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent out = 0x4000; 124135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent in -= 0x10000000; 125135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent } 126135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 127135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent j = 32 - __builtin_clz(in); 128135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 129135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent if (j & 1) j++; 130135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent j >>= 1; 131135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 132135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent for (i = j; i > 0; i--) { 133135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent tmp = (out << i) + (1 << ((i - 1)*2)); 134135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent if (in >= tmp) 135135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent { 136135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent out += 1 << (i-1); 137135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent in -= tmp; 138135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent } 139135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent } 140135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 141135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent return out; 142135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent} 143135ad07e33d30e5202deb21061a0e3ecf0ffad35Eric Laurent 144