Blender V2.61 - r43446
|
00001 /* 00002 * ***** BEGIN GPL LICENSE BLOCK ***** 00003 * 00004 * Copyright 2009-2011 Jörg Hermann Müller 00005 * 00006 * This file is part of AudaSpace. 00007 * 00008 * Audaspace is free software; you can redistribute it and/or modify 00009 * it under the terms of the GNU General Public License as published by 00010 * the Free Software Foundation; either version 2 of the License, or 00011 * (at your option) any later version. 00012 * 00013 * AudaSpace is distributed in the hope that it will be useful, 00014 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00015 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00016 * GNU General Public License for more details. 00017 * 00018 * You should have received a copy of the GNU General Public License 00019 * along with Audaspace; if not, write to the Free Software Foundation, 00020 * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 00021 * 00022 * ***** END GPL LICENSE BLOCK ***** 00023 */ 00024 00029 #include "AUD_JOSResampleReader.h" 00030 00031 #include "AUD_JOSResampleReaderCoeff.cpp" 00032 00033 #include <cmath> 00034 #include <cstring> 00035 #include <iostream> 00036 00037 /* MSVC does not have lrint */ 00038 #ifdef _MSC_VER 00039 #ifdef _M_X64 00040 #include <emmintrin.h> 00041 static inline int lrint(double d) 00042 { 00043 return _mm_cvtsd_si32(_mm_load_sd(&d)); 00044 } 00045 #else 00046 static inline int lrint(double d) 00047 { 00048 int i; 00049 00050 _asm{ 00051 fld d 00052 fistp i 00053 }; 00054 00055 return i; 00056 } 00057 #endif 00058 #endif 00059 00060 #define CC m_channels + channel 00061 00062 #define AUD_RATE_MAX 256 00063 #define SHIFT_BITS 12 00064 #define double_to_fp(x) (lrint(x * double(1 << SHIFT_BITS))) 00065 #define int_to_fp(x) (x << SHIFT_BITS) 00066 #define fp_to_int(x) (x >> SHIFT_BITS) 00067 #define fp_to_double(x) (x * 1.0/(1 << SHIFT_BITS)) 00068 #define fp_rest(x) (x & ((1 << SHIFT_BITS) - 1)) 00069 #define fp_rest_to_double(x) fp_to_double(fp_rest(x)) 00070 00071 AUD_JOSResampleReader::AUD_JOSResampleReader(AUD_Reference<AUD_IReader> reader, AUD_Specs specs) : 00072 AUD_ResampleReader(reader, specs.rate), 00073 m_channels(AUD_CHANNELS_INVALID), 00074 m_n(0), 00075 m_P(0), 00076 m_cache_valid(0), 00077 m_last_factor(0) 00078 { 00079 } 00080 00081 void AUD_JOSResampleReader::reset() 00082 { 00083 m_cache_valid = 0; 00084 m_n = 0; 00085 m_P = 0; 00086 m_last_factor = 0; 00087 } 00088 00089 void AUD_JOSResampleReader::updateBuffer(int size, double factor, int samplesize) 00090 { 00091 unsigned int len; 00092 double num_samples = double(m_len) / double(m_L); 00093 // first calculate what length we need right now 00094 if(factor >= 1) 00095 len = ceil(num_samples); 00096 else 00097 len = (unsigned int)(ceil(num_samples / factor)); 00098 00099 // then check if afterwards the length is enough for the maximum rate 00100 if(len + size < num_samples * AUD_RATE_MAX) 00101 len = num_samples * AUD_RATE_MAX - size; 00102 00103 if(m_n > len) 00104 { 00105 sample_t* buf = m_buffer.getBuffer(); 00106 len = m_n - len; 00107 memmove(buf, buf + len * m_channels, (m_cache_valid - len) * samplesize); 00108 m_n -= len; 00109 m_cache_valid -= len; 00110 } 00111 00112 m_buffer.assureSize((m_cache_valid + size) * samplesize, true); 00113 } 00114 00115 #define RESAMPLE_METHOD(name, left, right) void AUD_JOSResampleReader::name(double target_factor, int length, sample_t* buffer)\ 00116 {\ 00117 sample_t* buf = m_buffer.getBuffer();\ 00118 \ 00119 unsigned int P, l;\ 00120 int end, channel, i;\ 00121 double eta, v, f_increment, factor;\ 00122 \ 00123 m_sums.assureSize(m_channels * sizeof(double));\ 00124 double* sums = reinterpret_cast<double*>(m_sums.getBuffer());\ 00125 sample_t* data;\ 00126 const float* coeff = m_coeff;\ 00127 \ 00128 unsigned int P_increment;\ 00129 \ 00130 for(unsigned int t = 0; t < length; t++)\ 00131 {\ 00132 factor = (m_last_factor * (length - t - 1) + target_factor * (t + 1)) / length;\ 00133 \ 00134 memset(sums, 0, sizeof(double) * m_channels);\ 00135 \ 00136 if(factor >= 1)\ 00137 {\ 00138 P = double_to_fp(m_P * m_L);\ 00139 \ 00140 end = floor(m_len / double(m_L) - m_P) - 1;\ 00141 if(m_n < end)\ 00142 end = m_n;\ 00143 \ 00144 data = buf + (m_n - end) * m_channels;\ 00145 l = fp_to_int(P);\ 00146 eta = fp_rest_to_double(P);\ 00147 l += m_L * end;\ 00148 \ 00149 for(i = 0; i <= end; i++)\ 00150 {\ 00151 v = coeff[l] + eta * (coeff[l+1] - coeff[l]);\ 00152 l -= m_L;\ 00153 left\ 00154 }\ 00155 \ 00156 P = int_to_fp(m_L) - P;\ 00157 \ 00158 end = floor((m_len - 1) / double(m_L) + m_P) - 1;\ 00159 if(m_cache_valid - m_n - 2 < end)\ 00160 end = m_cache_valid - m_n - 2;\ 00161 \ 00162 data = buf + (m_n + 2 + end) * m_channels - 1;\ 00163 l = fp_to_int(P);\ 00164 eta = fp_rest_to_double(P);\ 00165 l += m_L * end;\ 00166 \ 00167 for(i = 0; i <= end; i++)\ 00168 {\ 00169 v = coeff[l] + eta * (coeff[l+1] - coeff[l]);\ 00170 l -= m_L;\ 00171 right\ 00172 }\ 00173 \ 00174 for(channel = 0; channel < m_channels; channel++)\ 00175 {\ 00176 *buffer = sums[channel];\ 00177 buffer++;\ 00178 }\ 00179 }\ 00180 else\ 00181 {\ 00182 f_increment = factor * m_L;\ 00183 P_increment = double_to_fp(f_increment);\ 00184 P = double_to_fp(m_P * f_increment);\ 00185 \ 00186 end = (int_to_fp(m_len) - P) / P_increment - 1;\ 00187 if(m_n < end)\ 00188 end = m_n;\ 00189 \ 00190 P += P_increment * end;\ 00191 data = buf + (m_n - end) * m_channels;\ 00192 l = fp_to_int(P);\ 00193 \ 00194 for(i = 0; i <= end; i++)\ 00195 {\ 00196 eta = fp_rest_to_double(P);\ 00197 v = coeff[l] + eta * (coeff[l+1] - coeff[l]);\ 00198 P -= P_increment;\ 00199 l = fp_to_int(P);\ 00200 left\ 00201 }\ 00202 \ 00203 P = -P;\ 00204 \ 00205 end = (int_to_fp(m_len) - P) / P_increment - 1;\ 00206 if(m_cache_valid - m_n - 2 < end)\ 00207 end = m_cache_valid - m_n - 2;\ 00208 \ 00209 P += P_increment * end;\ 00210 data = buf + (m_n + 2 + end) * m_channels - 1;\ 00211 l = fp_to_int(P);\ 00212 \ 00213 for(i = 0; i <= end; i++)\ 00214 {\ 00215 eta = fp_rest_to_double(P);\ 00216 v = coeff[l] + eta * (coeff[l+1] - coeff[l]);\ 00217 P -= P_increment;\ 00218 l = fp_to_int(P);\ 00219 right\ 00220 }\ 00221 \ 00222 for(channel = 0; channel < m_channels; channel++)\ 00223 {\ 00224 *buffer = factor * sums[channel];\ 00225 buffer++;\ 00226 }\ 00227 }\ 00228 \ 00229 m_P += fmod(1.0 / factor, 1.0);\ 00230 m_n += floor(1.0 / factor);\ 00231 \ 00232 while(m_P >= 1.0)\ 00233 {\ 00234 m_P -= 1.0;\ 00235 m_n++;\ 00236 }\ 00237 }\ 00238 } 00239 00240 RESAMPLE_METHOD(resample, { 00241 channel = 0; 00242 do 00243 { 00244 sums[channel] += *data * v; 00245 channel++; 00246 data++; 00247 } 00248 while(channel < m_channels); 00249 }, { 00250 channel = m_channels; 00251 do 00252 { 00253 channel--; 00254 sums[channel] += *data * v; 00255 data--; 00256 } 00257 while(channel); 00258 }) 00259 00260 RESAMPLE_METHOD(resample_mono, { 00261 *sums += *data * v; 00262 data++; 00263 }, { 00264 *sums += *data * v; 00265 data--; 00266 }) 00267 00268 RESAMPLE_METHOD(resample_stereo, { 00269 sums[0] += data[0] * v; 00270 sums[1] += data[1] * v; 00271 data+=2; 00272 }, { 00273 data-=2; 00274 sums[0] += data[1] * v; 00275 sums[1] += data[2] * v; 00276 }) 00277 00278 void AUD_JOSResampleReader::seek(int position) 00279 { 00280 position = floor(position * double(m_reader->getSpecs().rate) / double(m_rate)); 00281 m_reader->seek(position); 00282 reset(); 00283 } 00284 00285 int AUD_JOSResampleReader::getLength() const 00286 { 00287 return floor(m_reader->getLength() * double(m_rate) / double(m_reader->getSpecs().rate)); 00288 } 00289 00290 int AUD_JOSResampleReader::getPosition() const 00291 { 00292 return floor((m_reader->getPosition() + double(m_P)) 00293 * m_rate / m_reader->getSpecs().rate); 00294 } 00295 00296 AUD_Specs AUD_JOSResampleReader::getSpecs() const 00297 { 00298 AUD_Specs specs = m_reader->getSpecs(); 00299 specs.rate = m_rate; 00300 return specs; 00301 } 00302 00303 void AUD_JOSResampleReader::read(int& length, bool& eos, sample_t* buffer) 00304 { 00305 if(length == 0) 00306 return; 00307 00308 AUD_Specs specs = m_reader->getSpecs(); 00309 00310 int samplesize = AUD_SAMPLE_SIZE(specs); 00311 double target_factor = double(m_rate) / double(specs.rate); 00312 eos = false; 00313 int len; 00314 double num_samples = double(m_len) / double(m_L); 00315 00316 // check for channels changed 00317 if(specs.channels != m_channels) 00318 { 00319 m_channels = specs.channels; 00320 reset(); 00321 00322 switch(m_channels) 00323 { 00324 case AUD_CHANNELS_MONO: 00325 m_resample = &AUD_JOSResampleReader::resample_mono; 00326 break; 00327 case AUD_CHANNELS_STEREO: 00328 m_resample = &AUD_JOSResampleReader::resample_stereo; 00329 break; 00330 default: 00331 m_resample = &AUD_JOSResampleReader::resample; 00332 break; 00333 } 00334 } 00335 00336 if(m_last_factor == 0) 00337 m_last_factor = target_factor; 00338 00339 if(target_factor == 1 && m_last_factor == 1 && (m_P == 0)) 00340 { 00341 // can read directly! 00342 00343 len = length - (m_cache_valid - m_n); 00344 00345 updateBuffer(len, target_factor, samplesize); 00346 sample_t* buf = m_buffer.getBuffer(); 00347 00348 m_reader->read(len, eos, buf + m_cache_valid * m_channels); 00349 m_cache_valid += len; 00350 00351 length = m_cache_valid - m_n; 00352 00353 if(length > 0) 00354 { 00355 memcpy(buffer, buf + m_n * m_channels, length * samplesize); 00356 m_n += length; 00357 } 00358 00359 return; 00360 } 00361 00362 // use minimum for the following calculations 00363 double factor = AUD_MIN(target_factor, m_last_factor); 00364 00365 if(factor >= 1) 00366 len = (int(m_n) - m_cache_valid) + int(ceil(length / factor)) + ceil(num_samples); 00367 else 00368 len = (int(m_n) - m_cache_valid) + int(ceil(length / factor) + ceil(num_samples / factor)); 00369 00370 if(len > 0) 00371 { 00372 int should = len; 00373 00374 updateBuffer(len, factor, samplesize); 00375 00376 m_reader->read(len, eos, m_buffer.getBuffer() + m_cache_valid * m_channels); 00377 m_cache_valid += len; 00378 00379 if(len < should) 00380 { 00381 if(len == 0 && eos) 00382 length = 0; 00383 else 00384 { 00385 // use maximum for the following calculations 00386 factor = AUD_MAX(target_factor, m_last_factor); 00387 00388 if(eos) 00389 { 00390 // end of stream, let's check how many more samples we can produce 00391 len = floor((m_cache_valid - m_n) * factor); 00392 if(len < length) 00393 length = len; 00394 } 00395 else 00396 { 00397 // not enough data available yet, so we recalculate how many samples we can calculate 00398 if(factor >= 1) 00399 len = floor((num_samples + m_cache_valid - m_n) * factor); 00400 else 00401 len = floor((num_samples * factor + m_cache_valid - m_n) * factor); 00402 if(len < length) 00403 length = len; 00404 } 00405 } 00406 } 00407 } 00408 00409 (this->*m_resample)(target_factor, length, buffer); 00410 00411 m_last_factor = target_factor; 00412 00413 if(m_n > m_cache_valid) 00414 { 00415 m_n = m_cache_valid; 00416 } 00417 00418 eos = eos && ((m_n == m_cache_valid) || (length == 0)); 00419 }