From f828749c289bad5978ff3e7a8100c9a5c65b8970 Mon Sep 17 00:00:00 2001 From: "Matthias P. Braendli" Date: Tue, 6 Sep 2022 13:48:40 +0200 Subject: Replace libvlc compressor gain by internal gain calculation --- src/VLCInput.cpp | 9 +-------- src/VLCInput.h | 9 +-------- src/odr-audioenc.cpp | 36 ++++++++++++++++++++++++++---------- 3 files changed, 28 insertions(+), 26 deletions(-) (limited to 'src') diff --git a/src/VLCInput.cpp b/src/VLCInput.cpp index 0547696..ca44f04 100644 --- a/src/VLCInput.cpp +++ b/src/VLCInput.cpp @@ -1,5 +1,5 @@ /* ------------------------------------------------------------------ - * Copyright (C) 2018 Matthias P. Braendli + * Copyright (C) 2022 Matthias P. Braendli * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -169,10 +169,6 @@ void VLCInput::prepare() vlc_args.push_back("--network-caching=" + m_cache); } - if (not m_gain.empty()) { - vlc_args.push_back("--compressor-makeup=" + m_gain); - } - copy(m_additional_opts.begin(), m_additional_opts.end(), back_inserter(vlc_args)); @@ -204,9 +200,6 @@ void VLCInput::prepare() std::stringstream transcode_options_ss; transcode_options_ss << "acodec=fl32"; transcode_options_ss << ",samplerate=" << m_rate; - if (not m_gain.empty()) { - transcode_options_ss << ",afilter=compressor"; - } string transcode_options = transcode_options_ss.str(); char smem_options[512]; diff --git a/src/VLCInput.h b/src/VLCInput.h index 47a9cdd..ed1a682 100644 --- a/src/VLCInput.h +++ b/src/VLCInput.h @@ -1,5 +1,5 @@ /* ------------------------------------------------------------------ - * Copyright (C) 2017 Matthias P. Braendli + * Copyright (C) 2022 Matthias P. Braendli * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -54,7 +54,6 @@ class VLCInput : public InputInterface int rate, unsigned channels, unsigned verbosity, - std::string& gain, std::string& cache, std::vector& additional_opts, SampleQueue& queue) : @@ -64,7 +63,6 @@ class VLCInput : public InputInterface m_rate(rate), m_cache(cache), m_additional_opts(additional_opts), - m_gain(gain), m_vlc(nullptr), m_mp(nullptr), m_fault(false), @@ -136,11 +134,6 @@ class VLCInput : public InputInterface //! Given as-is to libvlc, useful for additional arguments std::vector m_additional_opts; - /*! value for the VLC compressor filter --compressor-makeup - * setting. Many more compressor settings could be set. - */ - std::string m_gain; - /*! VLC can give us the ICY-Text from an Icecast stream, * which we optionally write into a text file for ODR-PadEnc */ diff --git a/src/odr-audioenc.cpp b/src/odr-audioenc.cpp index 068c8a3..68a99a1 100644 --- a/src/odr-audioenc.cpp +++ b/src/odr-audioenc.cpp @@ -1,6 +1,6 @@ /* ------------------------------------------------------------------ * Copyright (C) 2011 Martin Storsjo - * Copyright (C) 2021 Matthias P. Braendli + * Copyright (C) 2022 Matthias P. Braendli * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -152,9 +152,6 @@ static void usage(const char* name) #if HAVE_VLC " -v, --vlc-uri=uri Enable VLC input and use the URI given as source\n" " -C, --vlc-cache=ms Specify VLC network cache length.\n" - " -g, --vlc-gain=db Enable VLC audio compressor, with given compressor-makeup value.\n" - " Use this as a workaround to correct the gain for streams that are\n" - " much too loud.\n" " -V Increase the VLC verbosity by one (can be given \n" " multiple times)\n" " -L OPTION Give an additional options to VLC (can be given\n" @@ -176,6 +173,9 @@ static void usage(const char* name) " -b, --bitrate={ 8, 16, ..., 192 } Output bitrate in kbps. Must be a multiple of 8.\n" " -c, --channels={ 1, 2 } Nb of input channels (default: 2).\n" " -r, --rate={ 24000, 32000, 48000 } Input sample rate (default: 48000).\n" + " -g, --audio-gain=dB Apply audio gain correction in dB to source, negative values allowed.\n" + " Use this as a workaround to correct the gain for streams that are\n" + " much too loud.\n" " DAB specific options\n" " -a, --dab Encode in DAB and not in DAB+.\n" " --dabmode=MODE Channel mode: s/d/j/m\n" @@ -405,6 +405,7 @@ struct AudioEnc { public: int sample_rate=48000; int channels=2; + double gain_dB = 0.0; string icytext_file; bool icytext_dlplus = false; @@ -420,7 +421,6 @@ public: // For the VLC input string vlc_uri; - string vlc_gain; string vlc_cache; vector vlc_additional_opts; unsigned verbosity = 0; @@ -1009,13 +1009,29 @@ int AudioEnc::run() * channels, and is formally wrong in mono, but still gives * numbers one can use. * + * At the same time, we apply gain correction. + * * \todo fix level measurement in mono */ int16_t peak_left = 0; int16_t peak_right = 0; + + const double linear_gain_correction = pow(10.0, gain_dB / 20.0); + for (int i = 0; i < read_bytes; i+=4) { int16_t l = input_buf[i] | (input_buf[i+1] << 8); int16_t r = input_buf[i+2] | (input_buf[i+3] << 8); + + if (linear_gain_correction != 1.0) { + l *= linear_gain_correction; + r *= linear_gain_correction; + + input_buf[i] = l & 0x00FF; + input_buf[i+1] = (l & 0xFF00) >> 8; + input_buf[i+2] = r & 0x00FF; + input_buf[i+3] = (r & 0xFF00) >> 8; + } + peak_left = std::max(peak_left, l); peak_right = std::max(peak_right, r); } @@ -1322,7 +1338,7 @@ shared_ptr AudioEnc::initialise_input() #if HAVE_VLC else if (not vlc_uri.empty()) { input = make_shared(vlc_uri, sample_rate, channels, verbosity, - vlc_gain, vlc_cache, vlc_additional_opts, queue); + vlc_cache, vlc_additional_opts, queue); } #endif #if HAVE_GST @@ -1353,6 +1369,7 @@ int main(int argc, char *argv[]) const struct option longopts[] = { {"bitrate", required_argument, 0, 'b'}, {"bandwidth", required_argument, 0, 'B'}, + {"audio-gain", required_argument, 0, 'g'}, {"channels", required_argument, 0, 'c'}, {"dabmode", required_argument, 0, 4 }, {"dabpsy", required_argument, 0, 5 }, @@ -1375,7 +1392,6 @@ int main(int argc, char *argv[]) {"startup-check", required_argument, 0, 9 }, {"stats", required_argument, 0, 'S'}, {"vlc-cache", required_argument, 0, 'C'}, - {"vlc-gain", required_argument, 0, 'g'}, {"vlc-uri", required_argument, 0, 'v'}, {"vlc-opt", required_argument, 0, 'L'}, {"write-icy-text", required_argument, 0, 'w'}, @@ -1516,6 +1532,9 @@ int main(int argc, char *argv[]) return 1; } break; + case 'g': + audio_enc.gain_dB = std::stod(optarg); + break; #ifdef HAVE_GST case 'G': audio_enc.gst_uri = optarg; @@ -1577,9 +1596,6 @@ int main(int argc, char *argv[]) case 'v': audio_enc.vlc_uri = optarg; break; - case 'g': - audio_enc.vlc_gain = optarg; - break; case 'C': audio_enc.vlc_cache = optarg; break; -- cgit v1.2.3