Commit 52d01e2f authored by Rafaël Carré's avatar Rafaël Carré

samplerateconverter: cleanup

Also resample the whole sample buffer given
parent bf11101c
......@@ -830,7 +830,6 @@ void AlsaLayer::audioCallback (void)
AudioLoop *file_tone;
SFLDataFormat *out = NULL;
SFLDataFormat *rsmpl_out = NULL;
notifyincomingCall();
......@@ -934,20 +933,12 @@ void AlsaLayer::audioCallback (void)
out[i] = out[i] * spkrVolume / 100;
if (_mainBufferSampleRate && ( (int) _audioSampleRate != _mainBufferSampleRate)) {
SFLDataFormat *rsmpl_out = (SFLDataFormat*) malloc (playbackAvailBytes);
memset (out, 0, playbackAvailBytes);
// Do sample rate conversion
int nb_sample_down = toGet / sizeof (SFLDataFormat);
if (rsmpl_out) {
rsmpl_out = (SFLDataFormat*) malloc (playbackAvailBytes);
memset (out, 0, playbackAvailBytes);
int nbSample = _converter->upsampleData ( (SFLDataFormat*) out, rsmpl_out, _mainBufferSampleRate, _audioSampleRate, nb_sample_down);
write (rsmpl_out, nbSample*sizeof (SFLDataFormat), _PlaybackHandle);
free (rsmpl_out);
}
rsmpl_out = 0;
_converter->upsampleData ( (SFLDataFormat*) out, rsmpl_out, _mainBufferSampleRate, _audioSampleRate, toGet / sizeof (SFLDataFormat));
write (rsmpl_out, toGet, _PlaybackHandle);
free (rsmpl_out);
} else {
......@@ -1035,14 +1026,11 @@ void AlsaLayer::audioCallback (void)
SFLDataFormat* rsmpl_out = (SFLDataFormat*) malloc (framesPerBufferAlsa * sizeof (SFLDataFormat));
int nbSample = toPut / sizeof (SFLDataFormat);
int nb_sample_up = nbSample;
nbSample = _converter->downsampleData ( (SFLDataFormat*) in, rsmpl_out, _mainBufferSampleRate, _audioSampleRate, nb_sample_up);
_converter->downsampleData ( (SFLDataFormat*) in, rsmpl_out, _mainBufferSampleRate, _audioSampleRate, toPut / sizeof (SFLDataFormat));
_audiofilter->processAudio (rsmpl_out, nbSample*sizeof (SFLDataFormat));
_audiofilter->processAudio (rsmpl_out, toPut);
getMainBuffer()->putData (rsmpl_out, nbSample * sizeof (SFLDataFormat));
getMainBuffer()->putData (rsmpl_out, toPut);
free (rsmpl_out);
} else {
......
......@@ -188,7 +188,9 @@ void AudioRtpRecordHandler::initBuffers()
// initialize SampleRate converter using AudioLayer's sampling rate
// (internal buffers initialized with maximal sampling rate and frame size)
_audioRtpRecord._converter = new SamplerateConverter ();
int rate = getCodecSampleRate();
int fs = getCodecFrameSize();
_audioRtpRecord._converter = new SamplerateConverter (rate, fs);
int nbSamplesMax = (int) ( (getCodecSampleRate() * getCodecFrameSize() / 1000));
_audioRtpRecord._micData = new SFLDataFormat[nbSamplesMax];
......@@ -262,47 +264,35 @@ int AudioRtpRecordHandler::processDataEncode (void)
unsigned char *micDataEncoded = _audioRtpRecord._micDataEncoded;
SFLDataFormat *micDataConverted = _audioRtpRecord._micDataConverted;
int codecFrameSize = getCodecFrameSize();
int codecSampleRate = getCodecSampleRate();
int mainBufferSampleRate = Manager::instance().getMainBuffer()->getInternalSamplingRate();
// compute codec framesize in ms
float fixedCodecFramesize = computeCodecFrameSize (codecFrameSize, codecSampleRate);
float fixedCodecFramesize = ((float)getCodecFrameSize() * 1000.0) / (float)codecSampleRate;
// compute nb of byte to get coresponding to 20 ms at audio layer frame size (44.1 khz)
int bytesToGet = computeNbByteAudioLayer (mainBufferSampleRate, fixedCodecFramesize);
// available bytes inside ringbuffer
int availBytesFromMic = Manager::instance().getMainBuffer()->availForGet (_id);
int bytesToGet = (int) ( ( (float) mainBufferSampleRate * fixedCodecFramesize * sizeof (SFLDataFormat)) / 1000.0);
if (availBytesFromMic < bytesToGet)
if (Manager::instance().getMainBuffer()->availForGet (_id) < bytesToGet)
return 0;
// Get bytes from micRingBuffer to data_from_mic
int nbSample = Manager::instance().getMainBuffer()->getData (micData, bytesToGet, _id) / sizeof (SFLDataFormat);
int bytes = Manager::instance().getMainBuffer()->getData (micData, bytesToGet, _id);
if (bytes == 0)
return 0;
// process mic fade in
if (!_audioRtpRecord._micFadeInComplete)
_audioRtpRecord._micFadeInComplete = fadeIn (micData, nbSample, &_audioRtpRecord._micAmplFactor);
if (nbSample == 0)
return nbSample;
_audioRtpRecord._micFadeInComplete = fadeIn (micData, bytes / sizeof(SFLDataFormat), &_audioRtpRecord._micAmplFactor);
// nb bytes to be sent over RTP
int compSize = 0;
int compSize;
// test if resampling is required
if (codecSampleRate != mainBufferSampleRate) {
int nbSampleUp = nbSample;
nbSample = _audioRtpRecord._converter->downsampleData (micData, micDataConverted, codecSampleRate, mainBufferSampleRate, nbSampleUp);
_audioRtpRecord._converter->downsampleData (micData, micDataConverted, codecSampleRate, mainBufferSampleRate, bytes / sizeof(SFLDataFormat));
_audioRtpRecord.audioProcessMutex.enter();
if (Manager::instance().audioPreference.getNoiseReduce()) {
_audioRtpRecord._audioProcess->processAudio (micDataConverted, nbSample * sizeof (SFLDataFormat));
_audioRtpRecord._audioProcess->processAudio (micDataConverted, bytes);
}
if(Manager::instance().getEchoCancelState() == "enabled") {
......@@ -313,22 +303,18 @@ int AudioRtpRecordHandler::processDataEncode (void)
_audioRtpRecord.audioCodecMutex.enter();
compSize = _audioRtpRecord._audioCodec->encode (micDataEncoded, micData, nbSample * sizeof (SFLDataFormat));
compSize = _audioRtpRecord._audioCodec->encode (micDataEncoded, micData, bytes);
_audioRtpRecord.audioCodecMutex.leave();
} else {
} else { // no resampling required
_audioRtpRecord.audioProcessMutex.enter();
if (Manager::instance().audioPreference.getNoiseReduce()) {
_audioRtpRecord._audioProcess->processAudio (micData, nbSample * sizeof (SFLDataFormat));
}
if (Manager::instance().audioPreference.getNoiseReduce())
_audioRtpRecord._audioProcess->processAudio (micData, bytes);
if(Manager::instance().getEchoCancelState() == "enabled") {
if(Manager::instance().getEchoCancelState() == "enabled")
echoCanceller.getData(micData);
}
#ifdef DUMP_PROCESS_DATA_ENCODE
teststream.write(reinterpret_cast<char *>(micData), nbSample * sizeof(SFLDataFormat));
......@@ -337,10 +323,7 @@ int AudioRtpRecordHandler::processDataEncode (void)
_audioRtpRecord.audioProcessMutex.leave();
_audioRtpRecord.audioCodecMutex.enter();
// no resampling required
compSize = _audioRtpRecord._audioCodec->encode (micDataEncoded, micData, nbSample * sizeof (SFLDataFormat));
compSize = _audioRtpRecord._audioCodec->encode (micDataEncoded, micData, bytes);
_audioRtpRecord.audioCodecMutex.leave();
}
......@@ -376,15 +359,14 @@ void AudioRtpRecordHandler::processDataDecode (unsigned char *spkrData, unsigned
// test if resampling is required
if (codecSampleRate != mainBufferSampleRate) {
// Do sample rate conversion
nbSample = _audioRtpRecord._converter->upsampleData (spkrDataDecoded, spkrDataConverted, codecSampleRate, mainBufferSampleRate, nbSample);
_audioRtpRecord._converter->upsampleData (spkrDataDecoded, spkrDataConverted, codecSampleRate, mainBufferSampleRate, nbSample);
if(Manager::instance().getEchoCancelState() == "enabled") {
echoCanceller.putData(spkrDataConverted, nbSample * sizeof(SFLDataFormat));
echoCanceller.putData(spkrDataConverted, expandedSize);
}
// put data in audio layer, size in byte
Manager::instance().getMainBuffer()->putData (spkrDataConverted, nbSample * sizeof (SFLDataFormat), _id);
Manager::instance().getMainBuffer()->putData (spkrDataConverted, expandedSize, _id);
} else {
if(Manager::instance().getEchoCancelState() == "enabled") {
......
......@@ -174,14 +174,6 @@ class AudioRtpRecordHandler
return _audioRtpRecord._micDataEncoded;
}
float computeCodecFrameSize (int codecSamplePerFrame, int codecClockRate) const {
return ( (float) codecSamplePerFrame * 1000.0) / (float) codecClockRate;
}
int computeNbByteAudioLayer (int mainBufferSamplingRate, float codecFrameSize) const {
return (int) ( ( (float) mainBufferSamplingRate * codecFrameSize * sizeof (SFLDataFormat)) / 1000.0);
}
void init (void);
/**
......
......@@ -768,7 +768,6 @@ void PulseLayer::writeToSpeaker (void)
pa_stream_write (playback->pulseStream(), out, copied * sizeof (SFLDataFormat), NULL, 0, PA_SEEK_RELATIVE);
pa_xfree (out);
}
}
else {
......@@ -794,11 +793,8 @@ void PulseLayer::writeToSpeaker (void)
byteToGet = (normalAvailBytes < (int) (maxNbBytesToGet)) ? normalAvailBytes : maxNbBytesToGet;
if (byteToGet) {
// Sending an odd number of byte breaks the audio!
if ( (byteToGet%2) != 0) {
byteToGet = byteToGet-1;
}
byteToGet &= ~1;
out = (SFLDataFormat*) pa_xmalloc (maxNbBytesToGet);
memset (out, 0, maxNbBytesToGet);
......@@ -807,29 +803,22 @@ void PulseLayer::writeToSpeaker (void)
// test if resampling is required
if (_mainBufferSampleRate && ( (int) _audioSampleRate != _mainBufferSampleRate)) {
SFLDataFormat* rsmpl_out = (SFLDataFormat*) pa_xmalloc (writeableSize);
memset (out, 0, writeableSize);
// Do sample rate conversion
int nb_sample_down = byteToGet / sizeof (SFLDataFormat);
_converter->upsampleData ( (SFLDataFormat*) out, rsmpl_out, _mainBufferSampleRate, _audioSampleRate, byteToGet / sizeof (SFLDataFormat));
int nbSample = _converter->upsampleData ( (SFLDataFormat*) out, rsmpl_out, _mainBufferSampleRate, _audioSampleRate, nb_sample_down);
if ( (nbSample*sizeof (SFLDataFormat)) > (unsigned int) writeableSize) {
if ( byteToGet > (unsigned int) writeableSize)
_warn ("Audio: Error: nbsbyte exceed buffer length");
}
// write resample data
pa_stream_write (playback->pulseStream(), rsmpl_out, nbSample*sizeof (SFLDataFormat), NULL, 0, PA_SEEK_RELATIVE);
pa_stream_write (playback->pulseStream(), rsmpl_out, byteToGet, NULL, 0, PA_SEEK_RELATIVE);
// free resampling buffer
pa_xfree (rsmpl_out);
} else {
// write origin data
pa_stream_write (playback->pulseStream(), out, byteToGet, NULL, 0, PA_SEEK_RELATIVE);
}
}
// free audio buffer used to get data from
pa_xfree (out);
......@@ -855,7 +844,6 @@ void PulseLayer::writeToSpeaker (void)
_urgentRingBuffer.Discard (byteToGet);
}
}
void PulseLayer::readFromMic (void)
......@@ -880,16 +868,12 @@ void PulseLayer::readFromMic (void)
SFLDataFormat* rsmpl_out = (SFLDataFormat*) pa_xmalloc (readableSize);
memset (rsmpl_out, 0, readableSize);
int nbSample = r / sizeof (SFLDataFormat);
int nb_sample_up = nbSample;
nbSample = _converter->downsampleData ( (SFLDataFormat *) data, rsmpl_out, _mainBufferSampleRate, _audioSampleRate, nb_sample_up);
_converter->downsampleData ( (SFLDataFormat *) data, rsmpl_out, _mainBufferSampleRate, _audioSampleRate, r / sizeof (SFLDataFormat));
// remove dc offset
_audiofilter->processAudio (rsmpl_out, nbSample*sizeof (SFLDataFormat));
_audiofilter->processAudio (rsmpl_out, r);
getMainBuffer()->putData (rsmpl_out, nbSample*sizeof (SFLDataFormat));
getMainBuffer()->putData (rsmpl_out, r);
pa_xfree (rsmpl_out);
......
......@@ -31,67 +31,19 @@
#include "samplerateconverter.h"
#include "manager.h"
SamplerateConverter::SamplerateConverter (int freq , int fs)
: _frequence (freq)
, _framesize (fs)
, _floatBufferDownMic (NULL)
SamplerateConverter::SamplerateConverter (int freq , int fs) :
_floatBufferDownMic (NULL)
, _floatBufferUpMic (NULL)
, _src_state_mic (NULL)
, _floatBufferDownSpkr (NULL)
, _floatBufferUpSpkr (NULL)
, _src_state_spkr (NULL)
, _src_err (0)
{
init();
}
SamplerateConverter::~SamplerateConverter (void)
{
if (_floatBufferUpMic) {
delete [] _floatBufferUpMic;
_floatBufferUpMic = NULL;
}
if (_floatBufferDownMic) {
delete [] _floatBufferDownMic;
_floatBufferDownMic = NULL;
}
if (_floatBufferUpSpkr) {
delete [] _floatBufferUpSpkr;
_floatBufferUpSpkr = NULL;
}
if (_floatBufferDownSpkr) {
delete [] _floatBufferDownSpkr;
_floatBufferDownSpkr = NULL;
}
// libSamplerateConverter-related
if (_src_state_mic) {
_src_state_mic = src_delete (_src_state_mic);
_src_state_mic = NULL;
}
if (_src_state_spkr) {
_src_state_spkr = src_delete (_src_state_spkr);
_src_state_spkr = NULL;
}
}
int err;
_src_state_mic = src_new (SRC_LINEAR, 1, &err);
_src_state_spkr = src_new (SRC_LINEAR, 1, &err);
void SamplerateConverter::init (void)
{
// libSamplerateConverter-related
// Set the converter type for the upsampling and the downsampling
// interpolator SRC_SINC_BEST_QUALITY
// interpolator SRC_SINC_FASTEST
// interpolator SRC_LINEAR
_src_state_mic = src_new (SRC_LINEAR, 1, &_src_err);
_src_state_spkr = src_new (SRC_LINEAR, 1, &_src_err);
int nbSamplesMax = (int) ( (_frequence * _framesize) / 1000);
int nbSamplesMax = (int) ( (freq * fs) / 1000);
_floatBufferDownMic = new float32[nbSamplesMax];
_floatBufferUpMic = new float32[nbSamplesMax];
......@@ -99,78 +51,71 @@ void SamplerateConverter::init (void)
_floatBufferUpSpkr = new float32[nbSamplesMax];
}
SamplerateConverter::~SamplerateConverter (void)
{
delete [] _floatBufferUpMic;
delete [] _floatBufferDownMic;
delete [] _floatBufferUpSpkr;
delete [] _floatBufferDownSpkr;
src_delete (_src_state_mic);
src_delete (_src_state_spkr);
}
void
SamplerateConverter::Short2FloatArray (const short *in, float *out, int len)
{
// factor is 1/(2^15), used to rescale the short int range to the
// [-1.0 - 1.0] float range.
#define S2F_FACTOR .000030517578125f;
while (len) {
len--;
out[len] = (float) in[len] * S2F_FACTOR;
}
while (len--)
out[len] = (float) in[len] * .000030517578125f;
}
//TODO Add ifdef for int16 or float32 type
int SamplerateConverter::upsampleData (SFLDataFormat* dataIn , SFLDataFormat* dataOut, int samplerate1 , int samplerate2 , int nbSamples)
void SamplerateConverter::upsampleData (SFLDataFormat* dataIn , SFLDataFormat* dataOut, int samplerate1 , int samplerate2 , int nbSamples)
{
double upsampleFactor = (double) samplerate2 / samplerate1 ;
int nbSamplesMax = (int) (samplerate2 * _framesize / 1000);
if (upsampleFactor != 1 && dataIn != NULL) {
SRC_DATA src_data;
src_data.data_in = _floatBufferDownSpkr;
src_data.data_out = _floatBufferUpSpkr;
src_data.input_frames = nbSamples;
src_data.output_frames = (int) floor (upsampleFactor * nbSamples);
src_data.src_ratio = upsampleFactor;
src_data.end_of_input = 0; // More data will come
// _debug(" upsample %d %d %f %d" , src_data.input_frames , src_data.output_frames, src_data.src_ratio , nbSamples);
// Override libsamplerate conversion function
Short2FloatArray (dataIn , _floatBufferDownSpkr, nbSamples);
//src_short_to_float_array (dataIn , _floatBufferDownSpkr, nbSamples);
//_debug("upsample %d %f %d" , src_data.output_frames, src_data.src_ratio , nbSamples);
src_process (_src_state_spkr, &src_data);
// _debug(" upsample %d %d %d" , samplerate1, samplerate2 , nbSamples);
nbSamples = (src_data.output_frames_gen > nbSamplesMax) ? nbSamplesMax : src_data.output_frames_gen;
src_float_to_short_array (_floatBufferUpSpkr, dataOut, nbSamples);
//_debug("upsample %d %d %d" , samplerate1, samplerate2 , nbSamples);
}
return nbSamples;
if (upsampleFactor == 1)
return;
SRC_DATA src_data;
src_data.data_in = _floatBufferDownSpkr;
src_data.data_out = _floatBufferUpSpkr;
src_data.input_frames = nbSamples;
src_data.output_frames = nbSamples;
src_data.src_ratio = upsampleFactor;
src_data.end_of_input = 0; // More data will come
Short2FloatArray (dataIn , _floatBufferDownSpkr, nbSamples);
src_process (_src_state_spkr, &src_data);
assert(nbSamples == src_data.output_frames_gen);
src_float_to_short_array (_floatBufferUpSpkr, dataOut, nbSamples);
}
//TODO Add ifdef for int16 or float32 type
int SamplerateConverter::downsampleData (SFLDataFormat* dataIn , SFLDataFormat* dataOut , int samplerate1 , int samplerate2 , int nbSamples)
void SamplerateConverter::downsampleData (SFLDataFormat* dataIn , SFLDataFormat* dataOut , int samplerate1 , int samplerate2 , int nbSamples)
{
double downsampleFactor = (double) samplerate1 / samplerate2;
int nbSamplesMax = (int) (samplerate1 * _framesize / 1000);
if (downsampleFactor != 1) {
SRC_DATA src_data;
src_data.data_in = _floatBufferUpMic;
src_data.data_out = _floatBufferDownMic;
src_data.input_frames = nbSamples;
src_data.output_frames = (int) floor (downsampleFactor * nbSamples);
src_data.src_ratio = downsampleFactor;
src_data.end_of_input = 0; // More data will come
//_debug("downsample %d %f %d" , src_data.output_frames, src_data.src_ratio , nbSamples);
// Override libsamplerate conversion function
Short2FloatArray (dataIn , _floatBufferUpMic, nbSamples);
//src_short_to_float_array (dataIn, _floatBufferUpMic, nbSamples);
//_debug("downsample %d %f %d" , src_data.output_frames, src_data.src_ratio , nbSamples);
src_process (_src_state_mic, &src_data);
//_debug("downsample %d %f %d" , src_data.output_frames, src_data.src_ratio , nbSamples);
nbSamples = (src_data.output_frames_gen > nbSamplesMax) ? nbSamplesMax : src_data.output_frames_gen;
//_debug("downsample %d %f %d" , src_data.output_frames, src_data.src_ratio , nbSamples);
src_float_to_short_array (_floatBufferDownMic , dataOut , nbSamples);
}
return nbSamples;
if (downsampleFactor == 1)
return;
SRC_DATA src_data;
src_data.data_in = _floatBufferUpMic;
src_data.data_out = _floatBufferDownMic;
src_data.input_frames = nbSamples;
src_data.output_frames = nbSamples;
src_data.src_ratio = downsampleFactor;
src_data.end_of_input = 0; // More data will come
Short2FloatArray (dataIn , _floatBufferUpMic, nbSamples);
src_process (_src_state_mic, &src_data);
assert(nbSamples == src_data.output_frames_gen);
src_float_to_short_array (_floatBufferDownMic , dataOut , nbSamples);
}
......@@ -47,7 +47,7 @@ class SamplerateConverter
* internal buffer size. Converter must be reinitialized
* every time these parameters change
*/
SamplerateConverter (int freq=44100, int frameSize=20);
SamplerateConverter (int freq, int frameSize);
/** Destructor */
~SamplerateConverter (void);
......@@ -58,9 +58,8 @@ class SamplerateConverter
* @param SamplerateConverter1 The lower sample rate
* @param SamplerateConverter2 The higher sample rate
* @param nbSamples The number of samples to process
* @return int The number of samples after the operation
*/
int upsampleData (SFLDataFormat* dataIn , SFLDataFormat* dataOut , int samplerate1 , int samplerate2 , int nbSamples);
void upsampleData (SFLDataFormat* dataIn , SFLDataFormat* dataOut , int samplerate1 , int samplerate2 , int nbSamples);
/**
* Downsample from the samplerate1 to the samplerate2
......@@ -68,9 +67,8 @@ class SamplerateConverter
* @param SamplerateConverter1 The lower sample rate
* @param SamplerateConverter2 The higher sample rate
* @param nbSamples The number of samples to process
* @return int The number of samples after the operation
*/
int downsampleData (SFLDataFormat* dataIn , SFLDataFormat* dataOut , int samplerate1 , int samplerate2 , int nbSamples);
void downsampleData (SFLDataFormat* dataIn , SFLDataFormat* dataOut , int samplerate1 , int samplerate2 , int nbSamples);
/**
* Convert short table to floats for audio processing
......@@ -88,12 +86,6 @@ class SamplerateConverter
// Assignment Operator
SamplerateConverter& operator= (const SamplerateConverter& rh);
void init (void);
/** Audio layer caracteristics */
int _frequence;
int _framesize;
/** Downsampled/Upsampled float buffers for the mic data processing */
float32* _floatBufferDownMic;
float32* _floatBufferUpMic;
......@@ -105,10 +97,6 @@ class SamplerateConverter
float32* _floatBufferUpSpkr;
/** libSamplerateConverter converter for incoming voice */
SRC_STATE* _src_state_spkr;
/** libSamplerateConverter error */
int _src_err;
};
#endif //_SAMPLE_RATE_H
......
......@@ -397,20 +397,19 @@ void WaveFile::openExistingWaveFile (const std::string& fileName, int audioSampl
while (remainingSamples > 0) {
int toProcess = remainingSamples > nbSampleMax ? nbSampleMax : remainingSamples;
int nbSamplesConverted = 0;
if (srate < audioSamplingRate) {
nbSamplesConverted = _converter.upsampleData (in, out, srate, audioSamplingRate, toProcess);
_converter.upsampleData (in, out, srate, audioSamplingRate, toProcess);
} else if (srate > audioSamplingRate) {
nbSamplesConverted = _converter.downsampleData (in, out, audioSamplingRate, srate, toProcess);
_converter.downsampleData (in, out, audioSamplingRate, srate, toProcess);
}
// nbSamplesConverted = nbSamplesConverted*2;
in += toProcess;
out += nbSamplesConverted;
out += toProcess;
remainingSamples -= toProcess;
totalprocessed += nbSamplesConverted;
totalprocessed += toProcess;
}
}
......
......@@ -315,7 +315,7 @@ IAXVoIPLink::sendAudioFromMic (void)
int compSize;
if (audioCodec->getClockRate() && ((int) audioCodec->getClockRate() != _mainBufferSampleRate)) {
// resample
bytes = converter->downsampleData (micData , micDataConverted , (int) audioCodec->getClockRate(), _mainBufferSampleRate, bytes);
converter->downsampleData (micData , micDataConverted , (int) audioCodec->getClockRate(), _mainBufferSampleRate, bytes);
compSize = audioCodec->encode (micDataEncoded, micDataConverted , bytes);
} else {
compSize = audioCodec->encode (micDataEncoded, micData, bytes);
......@@ -928,67 +928,47 @@ IAXVoIPLink::iaxHandleVoiceEvent (iax_event* event, IAXCall* call)
return;
if (audiolayer) {
_debug ("IAX: incoming audio, but no sound card open");
return;
}
Manager::instance().getMainBuffer ()->setInternalSamplingRate (audioCodec->getClockRate ());
// If we receive datalen == 0, some things of the jitter buffer in libiax2/iax.c
// were triggered
int _mainBufferSampleRate = Manager::instance().getMainBuffer()->getInternalSamplingRate();
// On-the-fly codec changing (normally, when we receive a full packet)
// as per http://tools.ietf.org/id/draft-guy-iax-03.txt
// - subclass holds the voiceformat property.
if (event->subclass && event->subclass != call->getFormat()) {
_debug ("iaxHandleVoiceEvent: no format found in call setting it to %i", event->subclass);
call->setFormat (event->subclass);
}
data = (unsigned char*) event->data;
size = event->datalen;
// Decode data with relevant codec
max = (int) (audioCodec->getClockRate() * audiolayer->getFrameSize() / 1000);
if (size > max) {
_debug ("The size %d is bigger than expected %d. Packet cropped. Ouch!", size, max);
size = max;
}
expandedSize = audioCodec->decode (spkrDataDecoded , data , size);
nbInt16 = expandedSize/sizeof (int16);
Manager::instance().getMainBuffer ()->setInternalSamplingRate (audioCodec->getClockRate ());
if (nbInt16 > max) {
_debug ("We have decoded an IAX VOICE packet larger than expected: %i VS %i. Cropping.", nbInt16, max);
nbInt16 = max;
}
// If we receive datalen == 0, some things of the jitter buffer in libiax2/iax.c
// were triggered
nbSample_ = nbInt16;
int _mainBufferSampleRate = Manager::instance().getMainBuffer()->getInternalSamplingRate();
// test if resampling is required
// On-the-fly codec changing (normally, when we receive a full packet)
// as per http://tools.ietf.org/id/draft-guy-iax-03.txt
// - subclass holds the voiceformat property.
if (audioCodec->getClockRate() && ((int) audioCodec->getClockRate() != _mainBufferSampleRate)) {
if (event->subclass && event->subclass != call->getFormat()) {
_debug ("iaxHandleVoiceEvent: no format found in call setting it to %i", event->subclass);
call->setFormat (event->subclass);
}
// resample
nbInt16 = converter->upsampleData (spkrDataDecoded, spkrDataConverted, audioCodec->getClockRate(), _mainBufferSampleRate, nbSample_);
data = (unsigned char*) event->data;
/* Write the data to the mic ring buffer */
audiolayer->getMainBuffer()->putData (spkrDataConverted, nbInt16 * sizeof (SFLDataFormat), call->getCallId());
size = event->datalen;
} else {
// Decode data with relevant codec
max = (int) (audioCodec->getClockRate() * audiolayer->getFrameSize() / 1000);
/* Write the data to the mic ring buffer */
audiolayer->getMainBuffer()->putData (spkrDataDecoded, nbInt16 * sizeof (SFLDataFormat), call->getCallId());
if (size > max) {
_debug ("The size %d is bigger than expected %d. Packet cropped. Ouch!", size, max);
size = max;
}
}
expandedSize = audioCodec->decode (spkrDataDecoded , data , size);
} else {
_debug ("IAX: incoming audio, but no sound card open");
}
if (audioCodec->getClockRate() && ((int) audioCodec->getClockRate() != _mainBufferSampleRate)) {
converter->upsampleData (spkrDataDecoded, spkrDataConverted, audioCodec->getClockRate(), _mainBufferSampleRate, expandedSize);
audiolayer->getMainBuffer()->putData (spkrDataConverted, expandedSize, call->getCallId());
} else {
audiolayer->getMainBuffer()->putData (spkrDataDecoded, expandedSize, call->getCallId());
}
}
/**
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment