From: bruceperens Date: Wed, 12 Mar 2014 04:30:50 +0000 (+0000) Subject: The pipeline works, tone plays through it. X-Git-Url: http://git.whiteaudio.com/gitweb/?a=commitdiff_plain;h=091febd64d1665ffdc297cf2b60b124b42c40537;p=freetel-svn-tracking.git The pipeline works, tone plays through it. git-svn-id: https://svn.code.sf.net/p/freetel/code@1427 01035d8c-6547-0410-b346-abe4f91aad63 --- diff --git a/freedv-server/source/drivers.h b/freedv-server/source/drivers.h index fb7f954e..f5fa2393 100644 --- a/freedv-server/source/drivers.h +++ b/freedv-server/source/drivers.h @@ -11,7 +11,7 @@ namespace FreeDV { /// the only reliable sample rate they all have in common. SampleRate /// may be lower than that and thus there may be resampling in the /// drivers. - const unsigned int SampleRate = 8000; + const unsigned int SampleRate = 48000; /// Allocate memory and copy a string into it, so that it is permanently /// stored. @@ -52,7 +52,9 @@ namespace FreeDV { /// \param length The amount of data requested. This must be smaller /// than or equal to the amount returned by get_available(). /// \return The address of the data to be read. - inline const uint8_t * get(std::size_t length) { + inline const uint8_t * + get(std::size_t length) { + assert(length % 2 == 0); if ( length > (std::size_t)(in - out) ) get_overrun(); return out; @@ -63,6 +65,7 @@ namespace FreeDV { /// This must be smaller than or equal to the amount passed to /// get(). inline void get_done(std::size_t length) { + assert(length % 2 == 0); out += length; assert(out >= buffer && out <= buffer_end); if ( out == in ) @@ -82,13 +85,14 @@ namespace FreeDV { /// You must call put_done(length) when the I/O is completed. /// The length passed to put_done() must be smaller than or equal /// to the length passed to put(). - /// \param io_length The size of buffer in chars requested. + /// \param length The size of buffer in chars requested. /// \return The address of the buffer for incoming data. - inline uint8_t * put(std::size_t io_length) { - const uint8_t * io_end = in + io_length; + inline uint8_t * put(std::size_t length) { + assert(length % 2 == 0); + const uint8_t * io_end = in + length; if ( io_end > buffer_end ) - return reorder(io_length); + return reorder(length); else return in; } @@ -97,6 +101,7 @@ namespace FreeDV { /// \param length The amount of data actually written. This must be /// smaller than or equal to the length passed to put(). inline void put_done(std::size_t length) { + assert(length % 2 == 0); in += length; assert(in >= buffer && in <= buffer_end); } diff --git a/freedv-server/source/modem_noop.cpp b/freedv-server/source/modem_noop.cpp index dedb96e8..42c4e907 100644 --- a/freedv-server/source/modem_noop.cpp +++ b/freedv-server/source/modem_noop.cpp @@ -87,7 +87,7 @@ namespace FreeDV { memcpy(o, i, length * 2); *sample_length = length; - return length; + return length * 2; } std::size_t diff --git a/freedv-server/source/platform/linux/audio_out_alsa.cpp b/freedv-server/source/platform/linux/audio_out_alsa.cpp index fdccc741..5b19696e 100644 --- a/freedv-server/source/platform/linux/audio_out_alsa.cpp +++ b/freedv-server/source/platform/linux/audio_out_alsa.cpp @@ -52,7 +52,7 @@ namespace FreeDV { const unsigned int channels = 1; const unsigned int rate = 48000; const int soft_resample = 0; - const unsigned int latency = 0; + const unsigned int latency = 10000; int error; handle = 0; @@ -90,9 +90,6 @@ namespace FreeDV { std::size_t AudioOutALSA::write16(const std::int16_t * array, std::size_t length) { - // for ( std::size_t i = 0 ; i < length ; i++ ) - // std::cerr << array[i] << ' '; - int result = snd_pcm_writei(handle, array, length); if ( result == -EPIPE ) { snd_pcm_recover(handle, result, 1); @@ -125,16 +122,18 @@ namespace FreeDV { AudioOutALSA::ready() { snd_pcm_sframes_t available = 0; + snd_pcm_sframes_t delay = 0; + int error; - available = snd_pcm_avail(handle); - if ( available == -EPIPE ) { - snd_pcm_recover(handle, available, 1); - available = snd_pcm_avail(handle); + error = snd_pcm_avail_delay(handle, &available, &delay); + if ( error == -EPIPE ) { + snd_pcm_recover(handle, error, 1); + available = snd_pcm_avail_delay(handle, &available, &delay); std::cerr << "ALSA write underrun." << std::endl; } - if ( available >= 0 ) + if ( error == 0 ) return available; - else if ( available == -EPIPE ) + else if ( error == -EPIPE ) return 0; else { do_throw(available, "Get Frames Available for Write"); diff --git a/freedv-server/source/run.cpp b/freedv-server/source/run.cpp index 5098a146..4bb7c46d 100644 --- a/freedv-server/source/run.cpp +++ b/freedv-server/source/run.cpp @@ -3,6 +3,7 @@ #include "drivers.h" #include #include +#include #include /// FIX: @@ -87,7 +88,7 @@ namespace FreeDV { std::cerr << "Keying output is stalled." << std::endl; } } - + // FIX: Parallelize the modem and codec into their own threads. Make the // FIFO do locking. void @@ -99,11 +100,6 @@ namespace FreeDV { (out_fifo.get_available() / 2)); if ( out_samples ) { - std::int16_t * s = (std::int16_t *)out_fifo.get(out_samples * 2); - - for ( std::size_t i = 0; i < out_samples; i++ ) { - std::cerr << (double)s[i] / 32767.0 << ' '; - } const std::size_t result = i->loudspeaker->write16( (std::int16_t *)out_fifo.get( out_samples * 2), @@ -142,6 +138,7 @@ namespace FreeDV { &samples_to_demodulate, bytes_to_demodulate); + if ( samples_to_demodulate > 0 ) in_fifo.get_done(samples_to_demodulate * 2); @@ -173,6 +170,7 @@ namespace FreeDV { Run::run() { while ( true ) { + usleep(1000); receive(); } } diff --git a/freedv-server/source/tone.cpp b/freedv-server/source/tone.cpp index dff8937a..1b6c5e44 100644 --- a/freedv-server/source/tone.cpp +++ b/freedv-server/source/tone.cpp @@ -5,6 +5,7 @@ #define _USE_MATH_DEFINES #include + namespace FreeDV { /// This is a test driver that provides tones. class Tone : public AudioInput { @@ -70,7 +71,7 @@ namespace FreeDV { input++; continue; } - if ( frequency < 0.0 || frequency > SampleRate ) { + if ( frequency < 0.0 || frequency > (SampleRate / 2) ) { std::cerr << "tone: frequency must be in range of 0.0.." << SampleRate / 2 << ", is " << frequency << '.' << std::endl; @@ -104,7 +105,7 @@ namespace FreeDV { float sumOfAmplitudes = 0; for ( unsigned int j = 0; j < array_length && tones[j].amplitude > 0.0; j++ ) { - value += (sine_wave(tones[j].frequency, i + clock) + value += (sine_wave(tones[j].frequency, clock + i) * tones[j].amplitude); // FIX: Hoist this out of the inner loop after it's tested. sumOfAmplitudes += tones[j].amplitude; @@ -113,7 +114,9 @@ namespace FreeDV { // sum of amplitudes is 1.0. if ( sumOfAmplitudes > 1.0 ) value /= sumOfAmplitudes; - array[i] = (std::int16_t)rint(value * master_amplitude * ((1 << 15) - 1)); + const std::int16_t v = (std::int16_t)rint( + value * master_amplitude * ((1 << 15) - 1)); + array[i] = v; } clock = (clock + length) % SampleRate;