コード例 #1
0
ファイル: rtp_audio_stream.cpp プロジェクト: DHODoS/wireshark
RtpAudioStream::RtpAudioStream(QObject *parent, _rtp_stream_info *rtp_stream) :
    QObject(parent),
    decoders_hash_(rtp_decoder_hash_table_new()),
    global_start_rel_time_(0.0),
    start_abs_offset_(0.0),
    start_rel_time_(0.0),
    stop_rel_time_(0.0),
    audio_out_rate_(0),
    audio_resampler_(0),
    audio_output_(0),
    max_sample_val_(1),
    color_(0),
    jitter_buffer_size_(50),
    timing_mode_(RtpAudioStream::JitterBuffer)
{
    copy_address(&src_addr_, &rtp_stream->src_addr);
    src_port_ = rtp_stream->src_port;
    copy_address(&dst_addr_, &rtp_stream->dest_addr);
    dst_port_ = rtp_stream->dest_port;
    ssrc_ = rtp_stream->ssrc;

    // We keep visual samples in memory. Make fewer of them.
    visual_resampler_ = speex_resampler_init(1, default_audio_sample_rate_,
                                                visual_sample_rate_, SPEEX_RESAMPLER_QUALITY_MIN, NULL);
    speex_resampler_skip_zeros(visual_resampler_);

    QString tempname = QString("%1/wireshark_rtp_stream").arg(QDir::tempPath());
    tempfile_ = new QTemporaryFile(tempname, this);
    tempfile_->open();

    // RTP_STREAM_DEBUG("Writing to %s", tempname.toUtf8().constData());
}
コード例 #2
0
AudioDecoderSpeex::AudioDecoderSpeex()
    : _speex_dec_state(speex_decoder_init(&speex_wb_mode)) 
{
    if (!_speex_dec_state) {
        throw MediaException(_("AudioDecoderSpeex: state initialization failed."));
    }

    speex_bits_init(&_speex_bits);

    speex_decoder_ctl(_speex_dec_state, SPEEX_GET_FRAME_SIZE, &_speex_framesize);

#ifdef RESAMPLING_SPEEX
    int err = 0;
    _resampler = speex_resampler_init(1, 16000, 44100,
        SPEEX_RESAMPLER_QUALITY_DEFAULT, &err);

    if (err != RESAMPLER_ERR_SUCCESS) {
        throw MediaException(_("AudioDecoderSpeex: initialization failed."));
    }

    spx_uint32_t num = 0, den = 0;

    speex_resampler_get_ratio (_resampler, &num, &den);
    assert(num && den);

    boost::rational<boost::uint32_t> numsamples(den, num);

    numsamples *= _speex_framesize * 2 /* convert to stereo */;

    _target_frame_size = boost::rational_cast<boost::uint32_t>(numsamples);
#endif
}
コード例 #3
0
AudioOutputSample::AudioOutputSample(const QString &name, SoundFile *psndfile, bool loop, unsigned int freq) : AudioOutputUser(name) {
	int err;

	sfHandle = psndfile;
	iOutSampleRate = freq;

	// Check if the file is good
	if (sfHandle->channels() <= 0 || sfHandle->channels() > 2) {
		sfHandle = NULL;
		return;
	}

	/* qWarning() << "Channels: " << sfHandle->channels();
	qWarning() << "Samplerate: " << sfHandle->samplerate();
	qWarning() << "Target Sr.: " << freq;
	qWarning() << "Format: " << sfHandle->format() << endl; */

	// If the frequencies don't match initialize the resampler
	if (sfHandle->samplerate() != static_cast<int>(freq)) {
		srs = speex_resampler_init(1, sfHandle->samplerate(), iOutSampleRate, 3, &err);
		if (err != RESAMPLER_ERR_SUCCESS) {
			qWarning() << "Initialize " << sfHandle->samplerate() << " to " << iOutSampleRate << " resampler failed!";
			srs = NULL;
			sfHandle = NULL;
			return;
		}
	} else {
		srs = NULL;
	}

	iLastConsume = iBufferFilled = 0;
	bLoop = loop;
	bEof = false;
}
コード例 #4
0
int create_resampler(uint32_t inSampleRate,
                    uint32_t outSampleRate,
                    uint32_t channelCount,
                    uint32_t quality,
                    struct resampler_buffer_provider* provider,
                    struct resampler_itfe **resampler)
{
    int error;
    struct resampler *rsmp;

    ALOGV("create_resampler() In SR %d Out SR %d channels %d",
         inSampleRate, outSampleRate, channelCount);

    if (resampler == NULL) {
        return -EINVAL;
    }

    *resampler = NULL;

    if (quality <= RESAMPLER_QUALITY_MIN || quality >= RESAMPLER_QUALITY_MAX) {
        return -EINVAL;
    }

    rsmp = (struct resampler *)calloc(1, sizeof(struct resampler));

    rsmp->speex_resampler = speex_resampler_init(channelCount,
                                      inSampleRate,
                                      outSampleRate,
                                      quality,
                                      &error);
    if (rsmp->speex_resampler == NULL) {
        ALOGW("ReSampler: Cannot create speex resampler: %s", speex_resampler_strerror(error));
        free(rsmp);
        return -ENODEV;
    }

    rsmp->itfe.reset = resampler_reset;
    rsmp->itfe.resample_from_provider = resampler_resample_from_provider;
    rsmp->itfe.resample_from_input = resampler_resample_from_input;
    rsmp->itfe.delay_ns = resampler_delay_ns;

    rsmp->provider = provider;
    rsmp->in_sample_rate = inSampleRate;
    rsmp->out_sample_rate = outSampleRate;
    rsmp->channel_count = channelCount;
    rsmp->in_buf = NULL;
    rsmp->in_buf_size = 0;

    resampler_reset(&rsmp->itfe);

    int frames = speex_resampler_get_input_latency(rsmp->speex_resampler);
    rsmp->speex_delay_ns = (int32_t)((1000000000 * (int64_t)frames) / rsmp->in_sample_rate);
    frames = speex_resampler_get_output_latency(rsmp->speex_resampler);
    rsmp->speex_delay_ns += (int32_t)((1000000000 * (int64_t)frames) / rsmp->out_sample_rate);

    *resampler = &rsmp->itfe;
    ALOGV("create_resampler() DONE rsmp %p &rsmp->itfe %p speex %p",
         rsmp, &rsmp->itfe, rsmp->speex_resampler);
    return 0;
}
コード例 #5
0
ファイル: Resampler.cpp プロジェクト: taqu/opus
    void Resampler::initialize()
    {
        if(dstSamplesPerSec_ == srcSamplesPerSec_){
            convertTypeFunc_ = getConvTypeFunc(
                dstNumChannels_,
                dstBytesPerSample_,
                srcNumChannels_,
                srcBytesPerSample_);

        }else{
            if(resamplerChannels_ != srcNumChannels_){
                destroyResampler();
            }
            if(NULL == resampler_){
                resampler_ = speex_resampler_init(srcNumChannels_, srcSamplesPerSec_, dstSamplesPerSec_, SPEEX_RESAMPLER_QUALITY_DEFAULT, NULL);
            }else{
                speex_resampler_set_rate(resampler_, srcSamplesPerSec_, dstSamplesPerSec_);
                speex_resampler_reset_mem(resampler_);
            }

            resampleRate_ = static_cast<f32>(dstSamplesPerSec_)/srcSamplesPerSec_;

            convertTypeFunc_ = getConvTypeFunc(
                dstNumChannels_,
                dstBytesPerSample_,
                srcNumChannels_,
                dstBytesPerSample_);
        }
    }
コード例 #6
0
cubeb_resampler *
cubeb_resampler_create(cubeb_stream * stream,
                       cubeb_stream_params params,
                       unsigned int out_rate,
                       cubeb_data_callback callback,
                       long buffer_frame_count,
                       void * user_ptr,
                       cubeb_resampler_quality quality)
{
  if (params.rate != out_rate) {
    SpeexResamplerState * resampler = NULL;
    resampler = speex_resampler_init(params.channels,
                                     params.rate,
                                     out_rate,
                                     to_speex_quality(quality),
                                     NULL);
    if (!resampler) {
      return NULL;
    }

    return new cubeb_resampler_speex(resampler, stream, params, out_rate,
                                     callback, buffer_frame_count, user_ptr);
  }

  return new noop_resampler(stream, callback, user_ptr);
}
コード例 #7
0
ファイル: AudioInput.cpp プロジェクト: fffonion/V8
void AudioInput::initializeMixer() {
	int err;

	if (srsMic)
		speex_resampler_destroy(srsMic);
	if (srsEcho)
		speex_resampler_destroy(srsEcho);
	if (pfMicInput)
		delete [] pfMicInput;
	if (pfEchoInput)
		delete [] pfEchoInput;
	if (pfOutput)
		delete [] pfOutput;

	if (iMicFreq != iSampleRate)
		srsMic = speex_resampler_init(1, iMicFreq, iSampleRate, 3, &err);

	iMicLength = (iFrameSize * iMicFreq) / iSampleRate;

	pfMicInput = new float[iMicLength];
	pfOutput = new float[iFrameSize * max(1U,iEchoChannels)];

	if (iEchoChannels > 0) {
		bEchoMulti = g_struct.s.bEchoMulti;
		if (iEchoFreq != iSampleRate)
			srsEcho = speex_resampler_init(bEchoMulti ? iEchoChannels : 1, iEchoFreq, iSampleRate, 3, &err);
		iEchoLength = (iFrameSize * iEchoFreq) / iSampleRate;
		iEchoMCLength = bEchoMulti ? iEchoLength * iEchoChannels : iEchoLength;
		iEchoFrameSize = bEchoMulti ? iFrameSize * iEchoChannels : iFrameSize;
		pfEchoInput = new float[iEchoMCLength];
	} else {
		srsEcho = NULL;
		pfEchoInput = NULL;
	}

	imfMic = chooseMixer(iMicChannels, eMicFormat);
	imfEcho = chooseMixer(iEchoChannels, eEchoFormat);

	iMicSampleSize = static_cast<int>(iMicChannels * ((eMicFormat == SampleFloat) ? sizeof(float) : sizeof(short)));
	iEchoSampleSize = static_cast<int>(iEchoChannels * ((eEchoFormat == SampleFloat) ? sizeof(float) : sizeof(short)));

	bResetProcessor = true;

	Trace("AudioInput: Initialized mixer for %d channel %d hz mic and %d channel %d hz echo", iMicChannels, iMicFreq, iEchoChannels, iEchoFreq);
}
コード例 #8
0
rl_resampler_t* rl_resampler_create( unsigned in_freq )
{
  if ( in_freq != RL_SAMPLE_RATE )
  {
    return (rl_resampler_t*)speex_resampler_init( 2, in_freq, RL_SAMPLE_RATE, RL_RESAMPLER_QUALITY, NULL );
  }
  
  return (rl_resampler_t*)&passthrough;
}
コード例 #9
0
static void resample_process_ms2(MSFilter *obj) {
    ResampleData *dt=(ResampleData*)obj->data;
    mblk_t *m;

    if (dt->output_rate==dt->input_rate) {
        while((m=ms_queue_get(obj->inputs[0]))!=NULL) {
            ms_queue_put(obj->outputs[0],m);
        }
        return;
    }
    ms_filter_lock(obj);
    if (dt->handle!=NULL) {
        unsigned int inrate=0, outrate=0;
        speex_resampler_get_rate(dt->handle,&inrate,&outrate);
        if (inrate!=dt->input_rate || outrate!=dt->output_rate) {
            speex_resampler_destroy(dt->handle);
            dt->handle=0;
        }
    }
    if (dt->handle==NULL) {
        int err=0;
        dt->handle=speex_resampler_init(dt->nchannels, dt->input_rate, dt->output_rate, SPEEX_RESAMPLER_QUALITY_VOIP, &err);
    }


    while((m=ms_queue_get(obj->inputs[0]))!=NULL) {
        unsigned int inlen=(m->b_wptr-m->b_rptr)/(2*dt->nchannels);
        unsigned int outlen=((inlen*dt->output_rate)/dt->input_rate)+1;
        unsigned int inlen_orig=inlen;
        mblk_t *om=allocb(outlen*2*dt->nchannels,0);
        if (dt->nchannels==1) {
            speex_resampler_process_int(dt->handle,
                                        0,
                                        (int16_t*)m->b_rptr,
                                        &inlen,
                                        (int16_t*)om->b_wptr,
                                        &outlen);
        } else {
            speex_resampler_process_interleaved_int(dt->handle,
                                                    (int16_t*)m->b_rptr,
                                                    &inlen,
                                                    (int16_t*)om->b_wptr,
                                                    &outlen);
        }
        if (inlen_orig!=inlen) {
            ms_error("Bug in resampler ! only %u samples consumed instead of %u, out=%u",
                     inlen,inlen_orig,outlen);
        }
        om->b_wptr+=outlen*2*dt->nchannels;
        mblk_set_timestamp_info(om,dt->ts);
        dt->ts+=outlen;
        ms_queue_put(obj->outputs[0],om);
        freemsg(m);
    }
    ms_filter_unlock(obj);
}
コード例 #10
0
static int resamp_new(struct ast_trans_pvt *pvt)
{
	int err;

	if (!(pvt->pvt = speex_resampler_init(1, ast_format_rate(&pvt->t->src_format), ast_format_rate(&pvt->t->dst_format), 5, &err))) {
		return -1;
	}

	return 0;
}
コード例 #11
0
nsresult
OpusTrackEncoder::Init(int aChannels, int aSamplingRate)
{
  // This monitor is used to wake up other methods that are waiting for encoder
  // to be completely initialized.
  ReentrantMonitorAutoEnter mon(mReentrantMonitor);

  NS_ENSURE_TRUE((aChannels <= MAX_SUPPORTED_AUDIO_CHANNELS) && (aChannels > 0),
                 NS_ERROR_FAILURE);

  // This version of encoder API only support 1 or 2 channels,
  // So set the mChannels less or equal 2 and
  // let InterleaveTrackData downmix pcm data.
  mChannels = aChannels > MAX_CHANNELS ? MAX_CHANNELS : aChannels;

  // Reject non-audio sample rates.
  NS_ENSURE_TRUE(aSamplingRate >= 8000, NS_ERROR_INVALID_ARG);
  NS_ENSURE_TRUE(aSamplingRate <= 192000, NS_ERROR_INVALID_ARG);

  // According to www.opus-codec.org, creating an opus encoder requires the
  // sampling rate of source signal be one of 8000, 12000, 16000, 24000, or
  // 48000. If this constraint is not satisfied, we resample the input to 48kHz.
  nsTArray<int> supportedSamplingRates;
  supportedSamplingRates.AppendElements(kOpusSupportedInputSamplingRates,
                         ArrayLength(kOpusSupportedInputSamplingRates));
  if (!supportedSamplingRates.Contains(aSamplingRate)) {
    int error;
    mResampler = speex_resampler_init(mChannels,
                                      aSamplingRate,
                                      kOpusSamplingRate,
                                      SPEEX_RESAMPLER_QUALITY_DEFAULT,
                                      &error);

    if (error != RESAMPLER_ERR_SUCCESS) {
      return NS_ERROR_FAILURE;
    }
  }
  mSamplingRate = aSamplingRate;
  NS_ENSURE_TRUE(mSamplingRate > 0, NS_ERROR_FAILURE);

  int error = 0;
  mEncoder = opus_encoder_create(GetOutputSampleRate(), mChannels,
                                 OPUS_APPLICATION_AUDIO, &error);


  mInitialized = (error == OPUS_OK);

  if (mAudioBitrate) {
    opus_encoder_ctl(mEncoder, OPUS_SET_BITRATE(static_cast<int>(mAudioBitrate)));
  }

  mReentrantMonitor.NotifyAll();

  return error == OPUS_OK ? NS_OK : NS_ERROR_FAILURE;
}
コード例 #12
0
ファイル: AudioInput.cpp プロジェクト: ArminW/re-whisper
void AudioInput::initializeMixer() {
	int err;

	if (srsMic)
		speex_resampler_destroy(srsMic);
	if (srsEcho)
		speex_resampler_destroy(srsEcho);
	if (pfMicInput)
		delete [] pfMicInput;
	if (pfEchoInput)
		delete [] pfEchoInput;
	if (pfOutput)
		delete [] pfOutput;

	if (iMicFreq != SAMPLE_RATE)
		srsMic = speex_resampler_init(1, iMicFreq, SAMPLE_RATE, 3, &err);

	iMicLength = (iFrameSize * iMicFreq) / SAMPLE_RATE;

	pfMicInput = new float[iMicLength];
	pfOutput = new float[iFrameSize];

	if (iEchoChannels > 0) {
		if (iEchoFreq != SAMPLE_RATE)
			srsEcho = speex_resampler_init(1, iEchoFreq, SAMPLE_RATE, 3, &err);
		iEchoLength = (iFrameSize * iEchoFreq) / SAMPLE_RATE;
		pfEchoInput = new float[iEchoLength];
	} else {
		srsEcho = NULL;
		pfEchoInput = NULL;
	}

	imfMic = chooseMixer(iMicChannels, eMicFormat);
	imfEcho = chooseMixer(iEchoChannels, eEchoFormat);

	iMicSampleSize = iMicChannels * ((eMicFormat == SampleFloat) ? sizeof(float) : sizeof(short));
	iEchoSampleSize = iEchoChannels * ((eEchoFormat == SampleFloat) ? sizeof(float) : sizeof(short));

	bResetProcessor = true;

	qWarning("AudioInput: Initialized mixer for %d channel %d hz mic and %d channel %d hz echo", iMicChannels, iMicFreq, iEchoChannels, iEchoFreq);
}
コード例 #13
0
int
Aulib::AudioResamplerSpeex::adjustForOutputSpec(unsigned dstRate, unsigned srcRate,
                                                unsigned channels)
{
    int err;
    d->fResampler.reset(speex_resampler_init(channels, srcRate, dstRate, 10, &err));
    if (err) {
        d->fResampler = nullptr;
        return -1;
    }
    return 0;
}
コード例 #14
0
ファイル: codec_resample.c プロジェクト: litnimax/asterisk
static int resamp_new(struct ast_trans_pvt *pvt)
{
	int err;

	if (!(pvt->pvt = speex_resampler_init(1, pvt->t->src_codec.sample_rate, pvt->t->dst_codec.sample_rate, 5, &err))) {
		return -1;
	}

	ast_assert(pvt->f.subclass.format == NULL);
	pvt->f.subclass.format = ao2_bump(ast_format_cache_get_slin_by_rate(pvt->t->dst_codec.sample_rate));

	return 0;
}
コード例 #15
0
static void resample_init_speex(ResampleData *dt){
	int err=0;
	int quality=SPEEX_RESAMPLER_QUALITY_VOIP; /*default value is voip*/
#if defined(__arm__) || defined(_M_ARM) /*on ARM, NEON optimization are mandatory to support this quality, else using basic mode*/
#if SPEEX_LIB_SET_CPU_FEATURES
	if (dt->cpuFeatures != SPEEX_LIB_CPU_FEATURE_NEON)
		quality=SPEEX_RESAMPLER_QUALITY_MIN;
#elif !defined(__ARM_NEON__)
	quality=SPEEX_RESAMPLER_QUALITY_MIN;
#endif /*SPEEX_LIB_SET_CPU_FEATURES*/
#endif /*defined(__arm__) || defined(_M_ARM)*/
	ms_message("Initializing speex resampler in mode [%s] ",(quality==SPEEX_RESAMPLER_QUALITY_VOIP?"voip":"min"));
	dt->handle=speex_resampler_init(dt->in_nchannels, dt->input_rate, dt->output_rate, quality, &err);
}
コード例 #16
0
ファイル: ebur128.c プロジェクト: andrewrk/libebur128
static int ebur128_init_resampler(ebur128_state* st) {
  int errcode = EBUR128_SUCCESS;

  if (st->samplerate < 96000) {
    st->d->oversample_factor = 4;
  } else if (st->samplerate < 192000) {
    st->d->oversample_factor = 2;
  } else {
    st->d->oversample_factor = 1;
    st->d->resampler_buffer_input = NULL;
    st->d->resampler_buffer_output = NULL;
    st->d->resampler = NULL;
  }

  st->d->resampler_buffer_input_frames = st->d->samples_in_100ms * 4;
  st->d->resampler_buffer_input = malloc(st->d->resampler_buffer_input_frames *
                                      st->channels *
                                      sizeof(float));
  CHECK_ERROR(!st->d->resampler_buffer_input, EBUR128_ERROR_NOMEM, exit)

  st->d->resampler_buffer_output_frames =
                                    st->d->resampler_buffer_input_frames *
                                    st->d->oversample_factor;
  st->d->resampler_buffer_output = malloc
                                      (st->d->resampler_buffer_output_frames *
                                       st->channels *
                                       sizeof(float));
  CHECK_ERROR(!st->d->resampler_buffer_output, EBUR128_ERROR_NOMEM, free_input)

  st->d->resampler = speex_resampler_init
                 ((spx_uint32_t) st->channels,
                  (spx_uint32_t) st->samplerate,
                  (spx_uint32_t) (st->samplerate * st->d->oversample_factor),
                  8, NULL);
  CHECK_ERROR(!st->d->resampler, EBUR128_ERROR_NOMEM, free_output)

  return errcode;

free_output:
  free(st->d->resampler_buffer_output);
  st->d->resampler_buffer_output = NULL;
free_input:
  free(st->d->resampler_buffer_input);
  st->d->resampler_buffer_input = NULL;
exit:
  return errcode;
}
コード例 #17
0
int CMAlsaAudioSink::init()
{
    int err;

    if ((err = snd_pcm_set_params(handle, SND_PCM_FORMAT_S16_LE, SND_PCM_ACCESS_RW_INTERLEAVED, m_channels, m_rate, 1, 100000)) < 0) {
        qDebug() << "Set params error: " << snd_strerror(err);
        return false;
    }
#if 0
    if (m_resampler)
        speex_resampler_destroy(m_resampler);

    m_resampler=speex_resampler_init(m_channels, m_rate, m_srate, 10, &err);
#endif

    return true;
}
コード例 #18
0
size_t
AudioNodeExternalInputStream::GetTrackMapEntry(const StreamBuffer::Track& aTrack,
                                               GraphTime aFrom)
{
  AudioSegment* segment = aTrack.Get<AudioSegment>();

  // Check the map for an existing entry corresponding to the input track.
  for (size_t i = 0; i < mTrackMap.Length(); ++i) {
    TrackMapEntry* map = &mTrackMap[i];
    if (map->mTrackID == aTrack.GetID()) {
      return i;
    }
  }

  // Determine channel count by finding the first entry with non-silent data.
  AudioSegment::ChunkIterator ci(*segment);
  while (!ci.IsEnded() && ci->IsNull()) {
    ci.Next();
  }
  if (ci.IsEnded()) {
    // The track is entirely silence so far, we can ignore it for now.
    return nsTArray<TrackMapEntry>::NoIndex;
  }

  // Create a speex resampler with the same sample rate and number of channels
  // as the track.
  SpeexResamplerState* resampler = nullptr;
  size_t channelCount = std::min((*ci).mChannelData.Length(),
                                   WebAudioUtils::MaxChannelCount);
  if (aTrack.GetRate() != mSampleRate) {
    resampler = speex_resampler_init(channelCount,
      aTrack.GetRate(), mSampleRate, SPEEX_RESAMPLER_QUALITY_DEFAULT, nullptr);
    speex_resampler_skip_zeros(resampler);
  }

  TrackMapEntry* map = mTrackMap.AppendElement();
  map->mEndOfConsumedInputTicks = 0;
  map->mEndOfLastInputIntervalInInputStream = -1;
  map->mEndOfLastInputIntervalInOutputStream = -1;
  map->mSamplesPassedToResampler =
    TimeToTicksRoundUp(aTrack.GetRate(), GraphTimeToStreamTime(aFrom));
  map->mResampler = resampler;
  map->mResamplerChannelCount = channelCount;
  map->mTrackID = aTrack.GetID();
  return mTrackMap.Length() - 1;
}
コード例 #19
0
	bool ResamplePCM(uint32 NumChannels, const TArray<uint8>& InBuffer, uint32 InSampleRate, TArray<uint8>& OutBuffer, uint32 OutSampleRate) const
	{
		// Initialize resampler to convert to desired rate for Opus
		int32 err = 0;
		SpeexResamplerState* resampler = speex_resampler_init(NumChannels, InSampleRate, OutSampleRate, SPEEX_RESAMPLER_QUALITY_DESKTOP, &err);
		if (err != RESAMPLER_ERR_SUCCESS)
		{
			speex_resampler_destroy(resampler);
			return false;
		}

		// Calculate extra space required for sample rate
		const uint32 SampleStride = SAMPLE_SIZE * NumChannels;
		const float Duration = (float)InBuffer.Num() / (InSampleRate * SampleStride);
		const int32 SafeCopySize = (Duration + 1) * OutSampleRate * SampleStride;
		OutBuffer.Empty(SafeCopySize);
		OutBuffer.AddUninitialized(SafeCopySize);
		uint32 InSamples = InBuffer.Num() / SampleStride;
		uint32 OutSamples = OutBuffer.Num() / SampleStride;

		// Do resampling and check results
		if (NumChannels == 1)
		{
			err = speex_resampler_process_int(resampler, 0, (const short*)(InBuffer.GetData()), &InSamples, (short*)(OutBuffer.GetData()), &OutSamples);
		}
		else
		{
			err = speex_resampler_process_interleaved_int(resampler, (const short*)(InBuffer.GetData()), &InSamples, (short*)(OutBuffer.GetData()), &OutSamples);
		}

		speex_resampler_destroy(resampler);
		if (err != RESAMPLER_ERR_SUCCESS)
		{
			return false;
		}

		// reduce the size of Out Buffer if more space than necessary was allocated
		const int32 WrittenBytes = (int32)(OutSamples * SampleStride);
		if (WrittenBytes < OutBuffer.Num())
		{
			OutBuffer.SetNum(WrittenBytes, true);
		}

		return true;
	}
コード例 #20
0
ファイル: resample_speex.c プロジェクト: deveck/Deveck.TAM
PJ_DEF(pj_status_t) pjmedia_resample_create( pj_pool_t *pool,
					     pj_bool_t high_quality,
					     pj_bool_t large_filter,
					     unsigned channel_count,
					     unsigned rate_in,
					     unsigned rate_out,
					     unsigned samples_per_frame,
					     pjmedia_resample **p_resample)
{
    pjmedia_resample *resample;
    int quality;
    int err;

    PJ_ASSERT_RETURN(pool && p_resample && rate_in &&
		     rate_out && samples_per_frame, PJ_EINVAL);

    resample = PJ_POOL_ZALLOC_T(pool, pjmedia_resample);
    PJ_ASSERT_RETURN(resample, PJ_ENOMEM);

    if (high_quality) {
	if (large_filter)
	    quality = 10;
	else
	    quality = 7;
    } else {
	quality = 3;
    }

    resample->in_samples_per_frame = samples_per_frame;
    resample->out_samples_per_frame = rate_out / (rate_in / samples_per_frame);
    resample->state = speex_resampler_init(channel_count,  rate_in, rate_out, 
                                           quality, &err);
    if (resample->state == NULL || err != RESAMPLER_ERR_SUCCESS)
	return PJ_ENOMEM;


    *p_resample = resample;

    PJ_LOG(5,(THIS_FILE, 
	      "resample created: quality=%d, ch=%d, in/out rate=%d/%d", 
	      quality, channel_count, rate_in, rate_out));
    return PJ_SUCCESS;
}
コード例 #21
0
ファイル: speex.c プロジェクト: RodrigoNieves/vlc
static int Open (vlc_object_t *obj)
{
    filter_t *filter = (filter_t *)obj;

    /* Will change rate */
    if (filter->fmt_in.audio.i_rate == filter->fmt_out.audio.i_rate
    /* Cannot convert format */
     || filter->fmt_in.audio.i_format != filter->fmt_out.audio.i_format
    /* Cannot remix */
     || filter->fmt_in.audio.i_physical_channels
                                  != filter->fmt_out.audio.i_physical_channels
     || filter->fmt_in.audio.i_original_channels
                                  != filter->fmt_out.audio.i_original_channels)
        return VLC_EGENERIC;

    switch (filter->fmt_in.audio.i_format)
    {
        case VLC_CODEC_FL32: break;
        case VLC_CODEC_S16N: break;
        default:             return VLC_EGENERIC;
    }

    SpeexResamplerState *st;

    unsigned channels = aout_FormatNbChannels (&filter->fmt_in.audio);
    unsigned q = var_InheritInteger (obj, "speex-resampler-quality");
    if (unlikely(q > 10))
        q = 3;

    int err;
    st = speex_resampler_init(channels, filter->fmt_in.audio.i_rate,
                              filter->fmt_out.audio.i_rate, q, &err);
    if (unlikely(st == NULL))
    {
        msg_Err (obj, "cannot initialize resampler: %s",
                 speex_resampler_strerror (err));
        return VLC_ENOMEM;
    }

    filter->p_sys = (filter_sys_t *)st;
    filter->pf_audio_filter = Resample;
    return VLC_SUCCESS;
}
コード例 #22
0
ファイル: speexdspResampler.c プロジェクト: taktod/ttLibC
/*
 * make speexdsp resampler.
 * @param channel_num        target channel num
 * @param input_sample_rate  input sample rate
 * @param output_sample_rate output sample rate
 * @param quality            quality for speexdsp resampler. 0:low quality - 10:max quality.
 * @return resampler object.
 */
ttLibC_SpeexdspResampler *ttLibC_SpeexdspResampler_make(uint32_t channel_num, uint32_t input_sample_rate, uint32_t output_sample_rate, uint32_t quality) {
	ttLibC_SpeexdspResampler_ *resampler = (ttLibC_SpeexdspResampler_ *)ttLibC_malloc(sizeof(ttLibC_SpeexdspResampler_));
	if(resampler == NULL) {
		ERR_PRINT("failed to allocate resampler object.");
		return NULL;
	}
	int error_num;
	resampler->resampler = speex_resampler_init(channel_num, input_sample_rate, output_sample_rate, quality, &error_num);
	if(error_num != 0 || resampler->resampler == NULL) {
		ERR_PRINT("failed to init speex resampler.");
		ttLibC_free(resampler);
		return NULL;
	}
	resampler->inherit_super.channel_num        = channel_num;
	resampler->inherit_super.input_sample_rate  = input_sample_rate;
	resampler->inherit_super.output_sample_rate = output_sample_rate;
	resampler->inherit_super.quality            = quality;
	return (ttLibC_SpeexdspResampler *)resampler;
}
コード例 #23
0
//==============================================================================
std::vector<float> AudioAnalysisManager::resamplePlot(std::vector<float> v)
{
    std::vector<float> resampledSignal;
    resampledSignal.resize(512);
    
    float *inF;
    inF = new float[v.size()];
    float *outF;
    outF = new float[v.size()];
    
    for (int i = 0;i < v.size();i++)
    {
        inF[i] = (float) v[i];
    }
    
    SpeexResamplerState *resampler;
    
    
    int err = 0;
    
    resampler = speex_resampler_init(1, (spx_uint32_t) v.size(), 512, 0, &err);
    
    
    spx_uint32_t inLen = (spx_uint32_t) v.size();
    spx_uint32_t outLen = (spx_uint32_t) 512;
    
    err = speex_resampler_process_float(resampler, 0, inF, &inLen, outF, &outLen);
    
    
    
    for (int i = 0;i < resampledSignal.size();i++)
    {
        resampledSignal[i] = outF[i];
    }
    
    delete [] inF;
    delete [] outF;
    
    speex_resampler_destroy(resampler);
    
    return resampledSignal;
}
コード例 #24
0
ファイル: audio_resampler.cpp プロジェクト: EasyRPG/Player
bool AudioResampler::Open(FILE* file) {
	if (wrapped_decoder->Open(file)) {
		wrapped_decoder->GetFormat(input_rate, input_format, nr_of_channels);

		//determine if the input format is supported by the resampler
		switch (input_format) {
			case Format::F32: output_format = input_format; break;
		#ifdef HAVE_LIBSPEEXDSP
			case Format::S16: output_format = input_format; break;
		#endif
			default: output_format = Format::F32; break;
		}

		//Set input format to output_format if possible
		wrapped_decoder->SetFormat(input_rate, output_format, nr_of_channels);
		//Reread format to get new values
		wrapped_decoder->GetFormat(input_rate, input_format, nr_of_channels);
		output_rate = input_rate;

		#if defined(HAVE_LIBSPEEXDSP)
			conversion_state = speex_resampler_init(nr_of_channels, input_rate, output_rate, sampling_quality, &lasterror);
			conversion_data.ratio_num = input_rate;
			conversion_data.ratio_denom = output_rate;
			speex_resampler_skip_zeros(conversion_state);
		#elif defined(HAVE_LIBSAMPLERATE)
			conversion_state = src_new(sampling_quality, nr_of_channels, &lasterror);
		#endif

		//Init the conversion data structure
		conversion_data.input_frames = 0;
		conversion_data.input_frames_used = 0;
		finished = false;

		if (conversion_state)
			return true;
	}

	conversion_state = nullptr;
	return false;
}
コード例 #25
0
bool COggVorbisFileHelper::init( std::string fin_str,bool bResample /*= true*/,int nResQuality/*=0*/, char* pData /*= NULL*/, uint32 iSize /*= 0*/)
{
	cleanup();

#if defined(HAVE_PTHREAD)
	pthread_mutex_lock(&mutex1);
#endif	

	nSoundChannel = s3eSoundGetFreeChannel();
	if(nSoundChannel == -1)
	{
		m_strLastError.clear();
		m_strLastError = "Cannot open a sound channel.";
		s3eDebugTracePrintf("%s\n",m_strLastError.c_str());
		cleanup();
#if defined(HAVE_PTHREAD)
		pthread_mutex_unlock(&mutex1);
#endif
		return false;
	}
	s3eSoundChannelRegister(nSoundChannel, S3E_CHANNEL_GEN_AUDIO, GenerateAudioCallback, this);
	s3eSoundChannelRegister(nSoundChannel, S3E_CHANNEL_END_SAMPLE, EndSampleCallback, this);

	ov_callbacks callbacks;
	callbacks.read_func = read_func;
	callbacks.seek_func = seek_func;
	callbacks.close_func = close_func;
	callbacks.tell_func = tell_func;

	if (pData != NULL)
	{
		oggvorbis_filein = s3eFileOpenFromMemory(pData, iSize);
	}
	else
	{
		if(false /*oggvorbis_filein != NULL*/)
		{
			if(s3eFileClose(oggvorbis_filein) == S3E_RESULT_ERROR)
			{
				m_strLastError.clear();
				m_strLastError = "Cannot close old file"; 
				s3eDebugTracePrintf("%s\n",m_strLastError.c_str());
				cleanup();
#if defined(HAVE_PTHREAD)
				pthread_mutex_unlock(&mutex1);
#endif
				return false;
			}
		}
		oggvorbis_filein = s3eFileOpen(fin_str.c_str(),"rb");
	}
	

	if(oggvorbis_filein == NULL)
	{
		m_strLastError.clear();
		m_strLastError = "Cannot open file " + fin_str; 
		s3eDebugTracePrintf("%s\n",m_strLastError.c_str());
		cleanup();
#if defined(HAVE_PTHREAD)
		pthread_mutex_unlock(&mutex1);
#endif
		return false;
	}

	if(ov_open_callbacks(oggvorbis_filein, &vf, NULL, 0, callbacks) < 0)
	{
		m_strLastError.clear();
		m_strLastError = "Input does not appear to be an Ogg bitstream.";
		s3eDebugTracePrintf("%s\n",m_strLastError.c_str());
		cleanup();
#if defined(HAVE_PTHREAD)
		pthread_mutex_unlock(&mutex1);
#endif
		return false;
	}

	/* Throw the comments plus a few lines about the bitstream we're
		decoding */
	{
		char **ptr=ov_comment(&vf,-1)->user_comments;
		vorbis_info *vi=ov_info(&vf,-1);
		//while(*ptr)
		//{
		//	fprintf(stderr,"%s\n",*ptr);
		//	++ptr;
		//}
		total_samples = ov_pcm_total(&vf,-1);
		time_length = ov_time_total_func(&vf,-1);
		nChannels = vi->channels;
		nRate	= vi->rate;

		s3eSoundChannelSetInt(nSoundChannel, S3E_CHANNEL_RATE, nRate);
		nOutputRate = s3eSoundGetInt(S3E_SOUND_OUTPUT_FREQ);

	
		int gcd = GCD(nRate, nOutputRate);
		nW = nRate  / gcd;
		nL = nOutputRate / gcd;


		dResampleFactor = (float)nOutputRate / (float)vi->rate;	// 0 - 4.0 ?

		int err;
		bEnableResampling = bResample;
		nResampleQuality = nResQuality;

		if(bEnableResampling)
		{
			if(res_contL)	speex_resampler_destroy(res_contL);
			res_contL =  speex_resampler_init(1,nRate,nOutputRate,nResampleQuality,&err);

			
			if(res_contR) speex_resampler_destroy(res_contR);
			res_contR =  speex_resampler_init(1,nRate,nOutputRate,nResampleQuality,&err);

			if(err != RESAMPLER_ERR_SUCCESS)
			{
				m_strLastError.clear();
				m_strLastError = "Cannot start resampler.";
				s3eDebugTracePrintf("%s\n",m_strLastError.c_str());
				cleanup();
#if defined(HAVE_PTHREAD)
				pthread_mutex_unlock(&mutex1);
#endif
				return false;
			}
		}
		else
		{
			int fs = min(nRate, nOutputRate);
			double fc = (fs/2) / (double)nOutputRate; // half the input sample rate (eg nyquist limit of input)
			// Generate filter coefficients
			wsfirLP(dFilterCoefficients, nFilterCoefficients, W_BLACKMAN, fc);

			if(dResampleFactor != 1)
				s3eDebugErrorShow(S3E_MESSAGE_CONTINUE,"Resample factor not 1 but resampling disabled");
		}


		s3eDebugTracePrintf("\nBitstream is %d channel, %ldHz\n",vi->channels,vi->rate);
		s3eDebugTracePrintf("\nDecoded length: %ld samples\n",(long)total_samples);
		s3eDebugTracePrintf("Encoded by: %s\n\n",ov_comment(&vf,-1)->vendor);
		s3eDebugTracePrintf("Resampling by rational factor %d / %d", nW, nL);
	}

	bStopDecoding = false;
	nStatus = OH_READY;
#if defined(HAVE_PTHREAD)
	pthread_mutex_unlock(&mutex1);
#endif
	return true;
}
コード例 #26
0
void
MediaDecodeTask::Decode()
{
  MOZ_ASSERT(!mThreadPool == NS_IsMainThread(),
             "We should be on the main thread only if we don't have a thread pool");

  mBufferDecoder->BeginDecoding(NS_GetCurrentThread());

  // Tell the decoder reader that we are not going to play the data directly,
  // and that we should not reject files with more channels than the audio
  // bakend support.
  mDecoderReader->SetIgnoreAudioOutputFormat();

  mDecoderReader->OnDecodeThreadStart();

  MediaInfo mediaInfo;
  nsAutoPtr<MetadataTags> tags;
  nsresult rv = mDecoderReader->ReadMetadata(&mediaInfo, getter_Transfers(tags));
  if (NS_FAILED(rv)) {
    ReportFailureOnMainThread(WebAudioDecodeJob::InvalidContent);
    return;
  }

  if (!mDecoderReader->HasAudio()) {
    ReportFailureOnMainThread(WebAudioDecodeJob::NoAudio);
    return;
  }

  while (mDecoderReader->DecodeAudioData()) {
    // consume all of the buffer
    continue;
  }

  mDecoderReader->OnDecodeThreadFinish();

  MediaQueue<AudioData>& audioQueue = mDecoderReader->AudioQueue();
  uint32_t frameCount = audioQueue.FrameCount();
  uint32_t channelCount = mediaInfo.mAudio.mChannels;
  uint32_t sampleRate = mediaInfo.mAudio.mRate;

  if (!frameCount || !channelCount || !sampleRate) {
    ReportFailureOnMainThread(WebAudioDecodeJob::InvalidContent);
    return;
  }

  const uint32_t destSampleRate = mDecodeJob.mContext->SampleRate();
  AutoResampler resampler;

  uint32_t resampledFrames = frameCount;
  if (sampleRate != destSampleRate) {
    resampledFrames = static_cast<uint32_t>(
        static_cast<uint64_t>(destSampleRate) *
        static_cast<uint64_t>(frameCount) /
        static_cast<uint64_t>(sampleRate)
      );

    resampler = speex_resampler_init(channelCount,
                                     sampleRate,
                                     destSampleRate,
                                     SPEEX_RESAMPLER_QUALITY_DEFAULT, nullptr);
    speex_resampler_skip_zeros(resampler);
    resampledFrames += speex_resampler_get_output_latency(resampler);
  }

  // Allocate the channel buffers.  Note that if we end up resampling, we may
  // write fewer bytes than mResampledFrames to the output buffer, in which
  // case mWriteIndex will tell us how many valid samples we have.
  static const fallible_t fallible = fallible_t();
  bool memoryAllocationSuccess = true;
  if (!mDecodeJob.mChannelBuffers.SetLength(channelCount)) {
    memoryAllocationSuccess = false;
  } else {
    for (uint32_t i = 0; i < channelCount; ++i) {
      mDecodeJob.mChannelBuffers[i] = new(fallible) float[resampledFrames];
      if (!mDecodeJob.mChannelBuffers[i]) {
        memoryAllocationSuccess = false;
        break;
      }
    }
  }
  if (!memoryAllocationSuccess) {
    ReportFailureOnMainThread(WebAudioDecodeJob::UnknownError);
    return;
  }

  nsAutoPtr<AudioData> audioData;
  while ((audioData = audioQueue.PopFront())) {
    audioData->EnsureAudioBuffer(); // could lead to a copy :(
    AudioDataValue* bufferData = static_cast<AudioDataValue*>
      (audioData->mAudioBuffer->Data());

    if (sampleRate != destSampleRate) {
      const uint32_t maxOutSamples = resampledFrames - mDecodeJob.mWriteIndex;

      for (uint32_t i = 0; i < audioData->mChannels; ++i) {
        uint32_t inSamples = audioData->mFrames;
        uint32_t outSamples = maxOutSamples;

        WebAudioUtils::SpeexResamplerProcess(
            resampler, i, &bufferData[i * audioData->mFrames], &inSamples,
            mDecodeJob.mChannelBuffers[i] + mDecodeJob.mWriteIndex,
            &outSamples);

        if (i == audioData->mChannels - 1) {
          mDecodeJob.mWriteIndex += outSamples;
          MOZ_ASSERT(mDecodeJob.mWriteIndex <= resampledFrames);
          MOZ_ASSERT(inSamples == audioData->mFrames);
        }
      }
    } else {
      for (uint32_t i = 0; i < audioData->mChannels; ++i) {
        ConvertAudioSamples(&bufferData[i * audioData->mFrames],
                            mDecodeJob.mChannelBuffers[i] + mDecodeJob.mWriteIndex,
                            audioData->mFrames);

        if (i == audioData->mChannels - 1) {
          mDecodeJob.mWriteIndex += audioData->mFrames;
        }
      }
    }
  }

  if (sampleRate != destSampleRate) {
    uint32_t inputLatency = speex_resampler_get_input_latency(resampler);
    const uint32_t maxOutSamples = resampledFrames - mDecodeJob.mWriteIndex;
    for (uint32_t i = 0; i < channelCount; ++i) {
      uint32_t inSamples = inputLatency;
      uint32_t outSamples = maxOutSamples;

      WebAudioUtils::SpeexResamplerProcess(
          resampler, i, (AudioDataValue*)nullptr, &inSamples,
          mDecodeJob.mChannelBuffers[i] + mDecodeJob.mWriteIndex,
          &outSamples);

      if (i == channelCount - 1) {
        mDecodeJob.mWriteIndex += outSamples;
        MOZ_ASSERT(mDecodeJob.mWriteIndex <= resampledFrames);
        MOZ_ASSERT(inSamples == inputLatency);
      }
    }
  }

  mPhase = PhaseEnum::AllocateBuffer;
  RunNextPhase();
}
コード例 #27
0
ThreadSharedFloatArrayBufferList*
AudioBuffer::GetThreadSharedChannelsForRate(JSContext* aJSContext, uint32_t aRate,
                                            uint32_t* aLength)
{
  if (mResampledChannels && mResampledChannelsRate == aRate) {
    // return cached data
    *aLength = mResampledChannelsLength;
    return mResampledChannels;
  }

  if (!mSharedChannels) {
    // Steal JS data
    mSharedChannels =
      StealJSArrayDataIntoThreadSharedFloatArrayBufferList(aJSContext, mJSChannels);
  }

  if (mSampleRate == aRate) {
    *aLength = mLength;
    return mSharedChannels;
  }

  mResampledChannels = new ThreadSharedFloatArrayBufferList(NumberOfChannels());

  double newLengthD = ceil(Duration()*aRate);
  uint32_t newLength = uint32_t(newLengthD);
  *aLength = newLength;
  double size = sizeof(float)*NumberOfChannels()*newLengthD;
  if (size != uint32_t(size)) {
    return mResampledChannels;
  }
  float* outputData = static_cast<float*>(malloc(uint32_t(size)));
  if (!outputData) {
    nsCOMPtr<nsPIDOMWindow> pWindow = do_QueryInterface(mContext->GetParentObject());
    nsIDocument* doc = nullptr;
    if (pWindow) {
      doc = pWindow->GetExtantDoc();
    }
    nsContentUtils::ReportToConsole(nsIScriptError::errorFlag,
                                    "Media",
                                    doc,
                                    nsContentUtils::eDOM_PROPERTIES,
                                    "MediaBufferSourceNodeResampleOutOfMemory");
    return mResampledChannels;
  }

  SpeexResamplerState* resampler = speex_resampler_init(NumberOfChannels(),
                                                        mSampleRate,
                                                        aRate,
                                                        SPEEX_RESAMPLER_QUALITY_DEFAULT,
                                                        nullptr);

  for (uint32_t i = 0; i < NumberOfChannels(); ++i) {
    const float* inputData = mSharedChannels->GetData(i);
    uint32_t inSamples = mLength;
    uint32_t outSamples = newLength;

    speex_resampler_process_float(resampler, i,
                                  inputData, &inSamples,
                                  outputData, &outSamples);

    mResampledChannels->SetData(i, i == 0 ? outputData : nullptr, outputData);
    outputData += newLength;
  }

  speex_resampler_destroy(resampler);

  mResampledChannelsRate = aRate;
  mResampledChannelsLength = newLength;
  return mResampledChannels;
}
コード例 #28
0
void BE_ST_InitAudio(void)
{
	g_sdlAudioSubsystemUp = false;
	g_sdlEmulatedOPLChipReady = false;
	int inSampleRate = BE_Cross_GetSelectedGameVerSampleRate();
	bool doDigitized = (inSampleRate != 0);
	if (!doDigitized)
		inSampleRate = OPL_SAMPLE_RATE;

	if (g_refKeenCfg.sndSubSystem)
	{
		if (SDL_InitSubSystem(SDL_INIT_AUDIO) < 0)
		{
			BE_Cross_LogMessage(BE_LOG_MSG_WARNING, "SDL audio system initialization failed,\n%s\n", SDL_GetError());
		}
		else
		{
			g_sdlAudioSpec.freq = g_refKeenCfg.sndSampleRate;
#ifdef MIXER_SAMPLE_FORMAT_FLOAT
			g_sdlAudioSpec.format = AUDIO_F32SYS;
#elif (defined MIXER_SAMPLE_FORMAT_SINT16)
			g_sdlAudioSpec.format = AUDIO_S16SYS;
#endif
			g_sdlAudioSpec.channels = 1;
			// Should be some power-of-two roughly proportional to the sample rate; Using 1024 for 48000Hz.
			for (g_sdlAudioSpec.samples = 1; g_sdlAudioSpec.samples < g_refKeenCfg.sndSampleRate/64; g_sdlAudioSpec.samples *= 2)
			{
			}

			if (doDigitized)
				g_sdlAudioSpec.callback = (g_refKeenCfg.sndSampleRate == inSampleRate) ? BEL_ST_Simple_DigiCallBack : BEL_ST_Resampling_DigiCallBack;
			else
				g_sdlAudioSpec.callback = ((g_refKeenCfg.sndSampleRate == inSampleRate) || !g_refKeenCfg.oplEmulation) ? BEL_ST_Simple_EmuCallBack : BEL_ST_Resampling_EmuCallBack;

			g_sdlAudioSpec.userdata = NULL;
			if (SDL_OpenAudio(&g_sdlAudioSpec, NULL))
			{
				BE_Cross_LogMessage(BE_LOG_MSG_WARNING, "Cannot open SDL audio device,\n%s\n", SDL_GetError());
				SDL_QuitSubSystem(SDL_INIT_AUDIO);
			}
			else
			{
#ifdef REFKEEN_CONFIG_THREADS
				g_sdlCallbackMutex = SDL_CreateMutex();
				if (!g_sdlCallbackMutex)
				{
					BE_Cross_LogMessage(BE_LOG_MSG_ERROR, "Cannot create recursive mutex for SDL audio callback,\n%s\nClosing SDL audio subsystem\n", SDL_GetError());
					SDL_CloseAudio();
					SDL_QuitSubSystem(SDL_INIT_AUDIO);
				}
				else
#endif
				{
					BE_Cross_LogMessage(BE_LOG_MSG_NORMAL, "Audio subsystem initialized, requested spec: freq %d, format %u, channels %d, samples %u\n", (int)g_sdlAudioSpec.freq, (unsigned int)g_sdlAudioSpec.format, (int)g_sdlAudioSpec.channels, (unsigned int)g_sdlAudioSpec.samples);
					g_sdlAudioSubsystemUp = true;
				}
			}
		}
	}
	// If the audio subsystem is off, let us simulate a byte rate
	// of 1000Hz (same as SDL_GetTicks() time units)
	if (!g_sdlAudioSubsystemUp)
	{
		g_sdlAudioSpec.freq = doDigitized ? inSampleRate : (NUM_OF_BYTES_FOR_SOUND_CALLBACK_WITH_DISABLED_SUBSYSTEM / sizeof(BE_ST_SndSample_T));
		g_sdlAudioSpec.callback = doDigitized ? BEL_ST_Resampling_DigiCallBack : BEL_ST_Resampling_EmuCallBack;
		return;
	}

	if (g_refKeenCfg.oplEmulation)
	{
		YM3812Init(1, 3579545, OPL_SAMPLE_RATE);
		g_sdlEmulatedOPLChipReady = true;
	}

	if ((doDigitized || g_sdlEmulatedOPLChipReady) && (g_sdlAudioSpec.freq != inSampleRate))
	{
		// Should allocate this first, for g_sdlSrcData.data_in
		g_sdlMiscOutNumOfSamples = 2*g_sdlAudioSpec.samples;
		g_sdlMiscOutSamples = (BE_ST_SndSample_T *)malloc(sizeof(BE_ST_SndSample_T) * g_sdlMiscOutNumOfSamples); 
		if (g_sdlMiscOutSamples == NULL)
			BE_ST_ExitWithErrorMsg("BE_ST_InitAudio: Out of memory! (Failed to allocate g_sdlMiscOutSamples.)");

#ifndef REFKEEN_RESAMPLER_NONE
		if (g_refKeenCfg.useResampler)
		{
#if (!defined REFKEEN_RESAMPLER_LIBRESAMPLE) && (!defined REFKEEN_RESAMPLER_LIBAVCODEC)
			char errMsg[160];
#endif

#if (defined REFKEEN_RESAMPLER_LIBSWRESAMPLE)
			g_sdlSwrContext = swr_alloc_set_opts(
				NULL,                // allocating a new context
				AV_CH_LAYOUT_MONO,   // out channels layout
				AV_SAMPLE_FMT_S16,   // out format
				g_sdlAudioSpec.freq, // out rate
				AV_CH_LAYOUT_MONO,   // in channels layout
				AV_SAMPLE_FMT_S16,   // in format
				inSampleRate,        // in rate
				0,
				NULL
			);
			if (g_sdlSwrContext == NULL)
				BE_ST_ExitWithErrorMsg("BE_ST_InitAudio: swr_alloc_set_opts failed!");
			int error = swr_init(g_sdlSwrContext);
			if (error != 0)
			{
				// av_err2str requires libavutil/libavutil-ffmpeg, so don't convert code to string
				snprintf(errMsg, sizeof(errMsg), "BE_ST_InitAudio: swr_init failed! Error code: %d", error);
				BE_ST_ExitWithErrorMsg(errMsg);
			}
#elif (defined REFKEEN_RESAMPLER_LIBAVRESAMPLE)
			g_sdlAvAudioResampleContext = avresample_alloc_context();
			if (g_sdlAvAudioResampleContext == NULL)
				BE_ST_ExitWithErrorMsg("BE_ST_InitAudio: avresample_alloc_context failed!");
			av_opt_set_int(g_sdlAvAudioResampleContext, "in_channel_layout",  AV_CH_LAYOUT_MONO,   0);
			av_opt_set_int(g_sdlAvAudioResampleContext, "out_channel_layout", AV_CH_LAYOUT_MONO,   0);
			av_opt_set_int(g_sdlAvAudioResampleContext, "in_sample_rate",     inSampleRate,        0);
			av_opt_set_int(g_sdlAvAudioResampleContext, "out_sample_rate",    g_sdlAudioSpec.freq, 0);
			av_opt_set_int(g_sdlAvAudioResampleContext, "in_sample_fmt",      AV_SAMPLE_FMT_S16,   0);
			av_opt_set_int(g_sdlAvAudioResampleContext, "out_sample_fmt",     AV_SAMPLE_FMT_S16,   0);
			int error = avresample_open(g_sdlAvAudioResampleContext);
			if (error != 0)
			{
				// av_err2str requires libavutil/libavutil-ffmpeg, so don't convert code to string
				snprintf(errMsg, sizeof(errMsg), "BE_ST_InitAudio: swr_init failed! Error code: %d", error);
				BE_ST_ExitWithErrorMsg(errMsg);
			}
#elif (defined REFKEEN_RESAMPLER_LIBAVCODEC)
			avcodec_register_all();
			g_sdlAvResampleContext = av_resample_init(
				g_sdlAudioSpec.freq,	// out rate
				inSampleRate,	// in rate
				16,	// filter length
				10,	// phase count
				0,	// linear FIR filter
				1.0	// cutoff frequency
			);
			if (g_sdlAvResampleContext == NULL)
				BE_ST_ExitWithErrorMsg("BE_ST_InitAudio: av_resample_init failed!");
#elif (defined REFKEEN_RESAMPLER_LIBRESAMPLE)
			g_sdlResampleFactor = (double)g_sdlAudioSpec.freq/inSampleRate;
			g_sdlResampleHandle = resample_open(0, g_sdlResampleFactor, g_sdlResampleFactor);
			if (g_sdlResampleHandle == NULL)
				BE_ST_ExitWithErrorMsg("BE_ST_InitAudio: resample_open failed!");
#elif (defined REFKEEN_RESAMPLER_LIBSOXR)
			soxr_io_spec_t io_spec = soxr_io_spec(SOXR_INT16, SOXR_INT16);
			soxr_quality_spec_t q_spec = soxr_quality_spec(SOXR_LQ, 0); // Default quality spec adds an audible latency for resampling to 8000Hz
			soxr_error_t error;
			g_sdlSoxr = soxr_create(
				inSampleRate, // in rate
				g_sdlAudioSpec.freq, // out rate
				1, // channels
				&error,
				&io_spec,
				&q_spec,
				NULL // runtime spec
			);
			if (g_sdlSoxr == NULL)
			{
				snprintf(errMsg, sizeof(errMsg), "BE_ST_InitAudio: soxr_create failed!\nError: %s", soxr_strerror(error));
				BE_ST_ExitWithErrorMsg(errMsg);
			}
#elif (defined REFKEEN_RESAMPLER_LIBSPEEXDSP)
			int error;
			g_sdlSpeexResamplerState = speex_resampler_init(
				1, // channels
				inSampleRate, // in rate
				g_sdlAudioSpec.freq, // out rate
				0, // quality in the range 0-10 (10 is higher)
				&error
			);
			if (g_sdlSpeexResamplerState == NULL)
			{
				snprintf(errMsg, sizeof(errMsg), "BE_ST_InitAudio: speex_resampler_init failed! Error code: %d\nError: %s", error, speex_resampler_strerror(error));
				BE_ST_ExitWithErrorMsg(errMsg);
			}
#elif (defined REFKEEN_RESAMPLER_LIBSAMPLERATE)
			int error;
			g_sdlSrcResampler = src_new(SRC_SINC_FASTEST, 1, &error);
			if (g_sdlSrcResampler == NULL)
			{
				snprintf(errMsg, sizeof(errMsg), "BE_ST_InitAudio: src_new failed!\nError code: %d", error);
				BE_ST_ExitWithErrorMsg(errMsg);
			}
			g_sdlSrcData.data_in = doDigitized ? g_sdlMiscOutSamples : g_sdlALOutSamples;
			g_sdlSrcData.src_ratio = (double)g_sdlAudioSpec.freq / inSampleRate;
#endif
		}
		else
#endif // REFKEEN_RESAMPLER_NONE
		{
			// The sum of all entries should be g_sdlAudioSpec.freq,
			// "uniformly" distributed over g_sdlALSampleRateConvTable
			g_sdlSampleRateConvTable = (int *)malloc(sizeof(int) * inSampleRate);
			if (g_sdlSampleRateConvTable == NULL)
				BE_ST_ExitWithErrorMsg("BE_ST_InitAudio: Failed to allocate memory for sample rate conversion!");
			g_sdlSampleRateConvTableSize = inSampleRate;
			for (int i = 0; i < inSampleRate; ++i)
			{
				// Using uint64_t cause an overflow is possible
				g_sdlSampleRateConvTable[i] = ((uint64_t)(i+1)*(uint64_t)g_sdlAudioSpec.freq/inSampleRate)-(uint64_t)i*(uint64_t)g_sdlAudioSpec.freq/inSampleRate;
			}
			g_sdlSampleRateConvCurrIndex = 0;
			g_sdlSampleRateConvCounter = 0;
		}
	}
}
コード例 #29
0
ファイル: speex_jni.c プロジェクト: jinglu-jlu/AudioTestSuite
JNIEXPORT jint JNICALL Java_com_zebra_emc_voip_audiotest_Speex_resample
  (JNIEnv * env, jclass obj, jstring path_in, jstring path_out, jint channels, jint sample_rate_in, jint sample_rate_out, jint quality) {

	// size in samples
	uint32_t in_size_in_sample;
	// size in samples
	uint32_t out_size_in_sample;
	// size in bytes (assumption: 2bytes/sample)
	uint32_t in_size;
	// size in bytes (assumption: 2bytes/sample)
	uint32_t out_size;
	short *in = NULL;
	short *out = NULL;
	FILE *fin = NULL;
	FILE *fout = NULL;
	SpeexResamplerState *st = NULL;

	if((channels != 1) && (channels !=2))
		return SPEEX_ERROR;

	const char *native_path = (*env)->GetStringUTFChars(env, path_in, 0);
	fin = fopen(native_path, "rb");
	(*env)->ReleaseStringUTFChars(env, path_in, native_path);
	if(NULL == fin)
		return SPEEX_ERROR;

	native_path = (*env)->GetStringUTFChars(env, path_out, 0);
	fout = fopen(native_path, "w+b");
	(*env)->ReleaseStringUTFChars(env, path_out, native_path);
	if(NULL == fout) {
		fclose(fin);
		return SPEEX_ERROR;
	}

	if(NULL == (st = speex_resampler_init(channels, sample_rate_in, sample_rate_out, SPEEX_RESAMPLER_QUALITY_DEFAULT, NULL)))
		return SPEEX_ERROR;

	in_size_in_sample = ((sample_rate_in * TIMEDURATION) / 1000) << (channels == 2 ? 1 : 0);
	in_size = in_size_in_sample * sizeof(short);
	out_size_in_sample = ((sample_rate_out * TIMEDURATION) / 1000) << (channels == 2 ? 1 : 0);
	out_size = out_size_in_sample * sizeof(short);

	in = malloc(in_size * sizeof(short));
	out = malloc(out_size * sizeof(short));

	uint32_t rd_len;
	int end_of_file = 0;
	int ret = SPEEX_SUCCESS;
	while (!end_of_file)
	{
		rd_len = fread(in, sizeof(short), in_size_in_sample, fin);
		if (rd_len < in_size_in_sample)
		{
			if(!feof(fin)) {
				ret = SPEEX_ERROR;
				break;
			}
			// the end of the file is reached
			else
				end_of_file = 1;
		}

		if(RESAMPLER_ERR_SUCCESS != speex_resampler_process_int(st, 0, in, &in_size_in_sample, out, &out_size_in_sample)) {
			ret = SPEEX_ERROR;
			break;
		}

		fwrite(out, sizeof(short), out_size_in_sample, fout);
	}
	speex_resampler_destroy(st);
	free(in);
	free(out);
	fclose(fin);
	fclose(fout);
	return ret;
}
コード例 #30
-1
ファイル: AudioOutput.cpp プロジェクト: pcgod/mumble-wip
AudioOutputSpeech::AudioOutputSpeech(boost::shared_ptr<ClientUser> user, MessageHandler::UDPMessageType type) : AudioOutputUser(user->qsName) {
	int err;
	p = user;
	umtType = type;

	unsigned int srate = 0;

	cCodec = NULL;
	cdDecoder = NULL;

	if (umtType != MessageHandler::UDPVoiceSpeex) {
		srate = SAMPLE_RATE;
		iFrameSize = srate / 100;

		dsSpeex = NULL;
	} else {
		speex_bits_init(&sbBits);

		dsSpeex = speex_decoder_init(speex_lib_get_mode(SPEEX_MODEID_UWB));
		int iArg=1;
		speex_decoder_ctl(dsSpeex, SPEEX_SET_ENH, &iArg);
		speex_decoder_ctl(dsSpeex, SPEEX_GET_FRAME_SIZE, &iFrameSize);
		speex_decoder_ctl(dsSpeex, SPEEX_GET_SAMPLING_RATE, &srate);
	}

	if (srate != SAMPLE_RATE)
		srs = speex_resampler_init(1, srate, SAMPLE_RATE, 3, &err);
	else
		srs = NULL;

	iOutputSize = static_cast<unsigned int>(ceilf(static_cast<float>(iFrameSize * SAMPLE_RATE) / static_cast<float>(SAMPLE_RATE)));

	iBufferOffset = iBufferFilled = iLastConsume = 0;
	bLastAlive = true;

	iMissCount = 0;
	iMissedFrames = 0;

	ucFlags = 0xFF;

	jbJitter = jitter_buffer_init(iFrameSize);
	int margin = g.s.iJitterBufferSize * iFrameSize;
	jitter_buffer_ctl(jbJitter, JITTER_BUFFER_SET_MARGIN, &margin);

	fFadeIn = new float[iFrameSize];
	fFadeOut = new float[iFrameSize];

	float mul = static_cast<float>(M_PI / (2.0 * static_cast<double>(iFrameSize)));
	for (unsigned int i=0;i<iFrameSize;++i)
		fFadeIn[i] = fFadeOut[iFrameSize-i-1] = sinf(static_cast<float>(i) * mul);
}