From 7715311117972984459dfbc1a4d8be9a83205b8c Mon Sep 17 00:00:00 2001
From: Rosen Penev <rosenp@gmail.com>
Date: Sun, 15 Mar 2020 23:33:21 -0700
Subject: [PATCH] fix double promotions

Found with -Wdouble-promotion

Signed-off-by: Rosen Penev <rosenp@gmail.com>
---
 src/ReplayGainGlobal.cxx                     | 12 ++++++------
 src/ReplayGainInfo.cxx                       | 12 ++++++------
 src/command/PlayerCommands.cxx               |  2 +-
 src/decoder/Bridge.cxx                       |  4 ++--
 src/decoder/plugins/MadDecoderPlugin.cxx     | 12 ++++++------
 src/decoder/plugins/OpusTags.cxx             |  4 ++--
 src/encoder/plugins/LameEncoderPlugin.cxx    |  8 ++++----
 src/encoder/plugins/TwolameEncoderPlugin.cxx |  6 +++---
 src/encoder/plugins/VorbisEncoderPlugin.cxx  |  8 ++++----
 src/mixer/plugins/PulseMixerPlugin.cxx       | 10 +++++-----
 src/mixer/plugins/SoftwareMixerPlugin.cxx    | 12 ++++++------
 src/output/Source.cxx                        |  2 +-
 src/pcm/FloatConvert.hxx                     |  2 +-
 src/pcm/PcmMix.cxx                           |  4 +++-
 src/pcm/SoxrResampler.cxx                    |  2 +-
 src/pcm/Volume.hxx                           |  2 +-
 src/queue/PlaylistState.cxx                  |  3 ++-
 17 files changed, 54 insertions(+), 51 deletions(-)

diff --git a/src/ReplayGainGlobal.cxx b/src/ReplayGainGlobal.cxx
index 56aaa7890..fc4306821 100644
--- a/src/ReplayGainGlobal.cxx
+++ b/src/ReplayGainGlobal.cxx
@@ -23,9 +23,9 @@
 #include "config/Data.hxx"
 #include "util/RuntimeError.hxx"
 
-#include <assert.h>
-#include <stdlib.h>
-#include <math.h>
+#include <cassert>
+#include <cstdlib>
+#include <cmath>
 
 static float
 ParsePreamp(const char *s)
@@ -33,14 +33,14 @@ ParsePreamp(const char *s)
 	assert(s != nullptr);
 
 	char *endptr;
-	float f = strtod(s, &endptr);
+	float f = std::strtof(s, &endptr);
 	if (endptr == s || *endptr != '\0')
 		throw std::invalid_argument("Not a numeric value");
 
-	if (f < -15 || f > 15)
+	if (f < -15.0f || f > 15.0f)
 		throw std::invalid_argument("Number must be between -15 and 15");
 
-	return pow(10, f / 20.0);
+	return std::pow(10.0f, f / 20.0f);
 }
 
 static float
diff --git a/src/ReplayGainInfo.cxx b/src/ReplayGainInfo.cxx
index 18f40ec4b..7963ff7be 100644
--- a/src/ReplayGainInfo.cxx
+++ b/src/ReplayGainInfo.cxx
@@ -20,7 +20,7 @@
 #include "ReplayGainInfo.hxx"
 #include "ReplayGainConfig.hxx"
 
-#include <math.h>
+#include <cmath>
 
 float
 ReplayGainTuple::CalculateScale(const ReplayGainConfig &config) const noexcept
@@ -28,13 +28,13 @@ ReplayGainTuple::CalculateScale(const ReplayGainConfig &config) const noexcept
 	float scale;
 
 	if (IsDefined()) {
-		scale = pow(10.0, gain / 20.0);
+		scale = std::pow(10.0f, gain / 20.0f);
 		scale *= config.preamp;
-		if (scale > 15.0)
-			scale = 15.0;
+		if (scale > 15.0f)
+			scale = 15.0f;
 
-		if (config.limit && scale * peak > 1.0)
-			scale = 1.0 / peak;
+		if (config.limit && scale * peak > 1.0f)
+			scale = 1.0f / peak;
 	} else
 		scale = config.missing_preamp;
 
diff --git a/src/command/PlayerCommands.cxx b/src/command/PlayerCommands.cxx
index e8d88e6cf..cf9438620 100644
--- a/src/command/PlayerCommands.cxx
+++ b/src/command/PlayerCommands.cxx
@@ -148,7 +148,7 @@ handle_status(Client &client, gcc_unused Request args, Response &r)
 		 playlist.GetConsume(),
 		 (unsigned long)playlist.GetVersion(),
 		 playlist.GetLength(),
-		 pc.GetMixRampDb(),
+		 (double)pc.GetMixRampDb(),
 		 state);
 
 	if (pc.GetCrossFade() > FloatDuration::zero())
diff --git a/src/decoder/Bridge.cxx b/src/decoder/Bridge.cxx
index e11a0a45a..9947bc3e5 100644
--- a/src/decoder/Bridge.cxx
+++ b/src/decoder/Bridge.cxx
@@ -33,11 +33,11 @@
 #include "util/ConstBuffer.hxx"
 #include "util/StringBuffer.hxx"
 
+#include <cmath>
 #include <stdexcept>
 
 #include <assert.h>
 #include <string.h>
-#include <math.h>
 
 DecoderBridge::~DecoderBridge()
 {
@@ -597,7 +597,7 @@ DecoderBridge::SubmitReplayGain(const ReplayGainInfo *new_replay_gain_info)
 			const auto &tuple = new_replay_gain_info->Get(rgm);
 			const auto scale =
 				tuple.CalculateScale(dc.replay_gain_config);
-			dc.replay_gain_db = 20.0 * log10f(scale);
+			dc.replay_gain_db = 20.0f * std::log10(scale);
 		}
 
 		replay_gain_info = *new_replay_gain_info;
diff --git a/src/decoder/plugins/MadDecoderPlugin.cxx b/src/decoder/plugins/MadDecoderPlugin.cxx
index b5a688bbf..a01a44001 100644
--- a/src/decoder/plugins/MadDecoderPlugin.cxx
+++ b/src/decoder/plugins/MadDecoderPlugin.cxx
@@ -617,8 +617,8 @@ parse_lame(struct lame *lame, struct mad_bitptr *ptr, int *bitlen) noexcept
 
 	mad_bit_skip(ptr, 16);
 
-	lame->peak = mad_f_todouble(mad_bit_read(ptr, 32) << 5); /* peak */
-	FormatDebug(mad_domain, "LAME peak found: %f", lame->peak);
+	lame->peak = MAD_F(mad_bit_read(ptr, 32) << 5); /* peak */
+	FormatDebug(mad_domain, "LAME peak found: %f", double(lame->peak));
 
 	lame->track_gain = 0;
 	unsigned name = mad_bit_read(ptr, 3); /* gain name */
@@ -626,9 +626,9 @@ parse_lame(struct lame *lame, struct mad_bitptr *ptr, int *bitlen) noexcept
 	unsigned sign = mad_bit_read(ptr, 1); /* sign bit */
 	int gain = mad_bit_read(ptr, 9); /* gain*10 */
 	if (gain && name == 1 && orig != 0) {
-		lame->track_gain = ((sign ? -gain : gain) / 10.0) + adj;
+		lame->track_gain = ((sign ? -gain : gain) / 10.0f) + adj;
 		FormatDebug(mad_domain, "LAME track gain found: %f",
-			    lame->track_gain);
+			    double(lame->track_gain));
 	}
 
 	/* tmz reports that this isn't currently written by any version of lame
@@ -644,7 +644,7 @@ parse_lame(struct lame *lame, struct mad_bitptr *ptr, int *bitlen) noexcept
 	if (gain && name == 2 && orig != 0) {
 		lame->album_gain = ((sign ? -gain : gain) / 10.0) + adj;
 		FormatDebug(mad_domain, "LAME album gain found: %f",
-			    lame->track_gain);
+			    double(lame->track_gain));
 	}
 #else
 	mad_bit_skip(ptr, 16);
@@ -778,7 +778,7 @@ MadDecoder::DecodeFirstFrame(Tag *tag) noexcept
 			/* Album gain isn't currently used.  See comment in
 			 * parse_lame() for details. -- jat */
 			if (client != nullptr && !found_replay_gain &&
-			    lame.track_gain) {
+			    lame.track_gain > 0.0f) {
 				ReplayGainInfo rgi;
 				rgi.Clear();
 				rgi.track.gain = lame.track_gain;
diff --git a/src/decoder/plugins/OpusTags.cxx b/src/decoder/plugins/OpusTags.cxx
index 76ea63e6e..70e452860 100644
--- a/src/decoder/plugins/OpusTags.cxx
+++ b/src/decoder/plugins/OpusTags.cxx
@@ -53,7 +53,7 @@ ScanOneOpusTag(const char *name, const char *value,
 		char *endptr;
 		long l = strtol(value, &endptr, 10);
 		if (endptr > value && *endptr == 0)
-			rgi->track.gain = double(l) / 256.;
+			rgi->track.gain = float(l) / 256.0f;
 	} else if (rgi != nullptr &&
 		   StringEqualsCaseASCII(name, "R128_ALBUM_GAIN")) {
 		/* R128_ALBUM_GAIN is a Q7.8 fixed point number in
@@ -62,7 +62,7 @@ ScanOneOpusTag(const char *name, const char *value,
 		char *endptr;
 		long l = strtol(value, &endptr, 10);
 		if (endptr > value && *endptr == 0)
-			rgi->album.gain = double(l) / 256.;
+			rgi->album.gain = float(l) / 256.0f;
 	}
 
 	handler.OnPair(name, value);
diff --git a/src/encoder/plugins/LameEncoderPlugin.cxx b/src/encoder/plugins/LameEncoderPlugin.cxx
index fe663c28c..7f6df6eb0 100644
--- a/src/encoder/plugins/LameEncoderPlugin.cxx
+++ b/src/encoder/plugins/LameEncoderPlugin.cxx
@@ -77,9 +77,9 @@ PreparedLameEncoder::PreparedLameEncoder(const ConfigBlock &block)
 	if (value != nullptr) {
 		/* a quality was configured (VBR) */
 
-		quality = ParseDouble(value, &endptr);
+		quality = float(ParseDouble(value, &endptr));
 
-		if (*endptr != '\0' || quality < -1.0 || quality > 10.0)
+		if (*endptr != '\0' || quality < -1.0f || quality > 10.0f)
 			throw FormatRuntimeError("quality \"%s\" is not a number in the "
 						 "range -1 to 10",
 						 value);
@@ -111,13 +111,13 @@ static void
 lame_encoder_setup(lame_global_flags *gfp, float quality, int bitrate,
 		   const AudioFormat &audio_format)
 {
-	if (quality >= -1.0) {
+	if (quality >= -1.0f) {
 		/* a quality was configured (VBR) */
 
 		if (0 != lame_set_VBR(gfp, vbr_rh))
 			throw std::runtime_error("error setting lame VBR mode");
 
-		if (0 != lame_set_VBR_q(gfp, quality))
+		if (0 != lame_set_VBR_q(gfp, int(quality)))
 			throw std::runtime_error("error setting lame VBR quality");
 	} else {
 		/* a bit rate was configured */
diff --git a/src/encoder/plugins/TwolameEncoderPlugin.cxx b/src/encoder/plugins/TwolameEncoderPlugin.cxx
index e05f64764..debed7871 100644
--- a/src/encoder/plugins/TwolameEncoderPlugin.cxx
+++ b/src/encoder/plugins/TwolameEncoderPlugin.cxx
@@ -95,9 +95,9 @@ PreparedTwolameEncoder::PreparedTwolameEncoder(const ConfigBlock &block)
 	if (value != nullptr) {
 		/* a quality was configured (VBR) */
 
-		quality = ParseDouble(value, &endptr);
+		quality = float(ParseDouble(value, &endptr));
 
-		if (*endptr != '\0' || quality < -1.0 || quality > 10.0)
+		if (*endptr != '\0' || quality < -1.0f || quality > 10.0f)
 			throw FormatRuntimeError("quality \"%s\" is not a number in the "
 						 "range -1 to 10",
 						 value);
@@ -132,7 +132,7 @@ static void
 twolame_encoder_setup(twolame_options *options, float quality, int bitrate,
 		      const AudioFormat &audio_format)
 {
-	if (quality >= -1.0) {
+	if (quality >= -1.0f) {
 		/* a quality was configured (VBR) */
 
 		if (0 != twolame_set_VBR(options, true))
diff --git a/src/encoder/plugins/VorbisEncoderPlugin.cxx b/src/encoder/plugins/VorbisEncoderPlugin.cxx
index 7a17a77f3..90a8120c6 100644
--- a/src/encoder/plugins/VorbisEncoderPlugin.cxx
+++ b/src/encoder/plugins/VorbisEncoderPlugin.cxx
@@ -84,7 +84,7 @@ PreparedVorbisEncoder::PreparedVorbisEncoder(const ConfigBlock &block)
 		char *endptr;
 		quality = ParseDouble(value, &endptr);
 
-		if (*endptr != '\0' || quality < -1.0 || quality > 10.0)
+		if (*endptr != '\0' || quality < -1.0f || quality > 10.0f)
 			throw FormatRuntimeError("quality \"%s\" is not a number in the "
 						 "range -1 to 10",
 						 value);
@@ -122,13 +122,13 @@ VorbisEncoder::VorbisEncoder(float quality, int bitrate,
 	_audio_format.format = SampleFormat::FLOAT;
 	audio_format = _audio_format;
 
-	if (quality >= -1.0) {
+	if (quality >= -1.0f) {
 		/* a quality was configured (VBR) */
 
 		if (0 != vorbis_encode_init_vbr(&vi,
 						audio_format.channels,
 						audio_format.sample_rate,
-						quality * 0.1)) {
+						quality * 0.1f)) {
 			vorbis_info_clear(&vi);
 			throw std::runtime_error("error initializing vorbis vbr");
 		}
@@ -138,7 +138,7 @@ VorbisEncoder::VorbisEncoder(float quality, int bitrate,
 		if (0 != vorbis_encode_init(&vi,
 					    audio_format.channels,
 					    audio_format.sample_rate, -1.0,
-					    bitrate * 1000, -1.0)) {
+					    bitrate * 1000, -1.0f)) {
 			vorbis_info_clear(&vi);
 			throw std::runtime_error("error initializing vorbis encoder");
 		}
diff --git a/src/mixer/plugins/PulseMixerPlugin.cxx b/src/mixer/plugins/PulseMixerPlugin.cxx
index 44fcb56f7..f39044459 100644
--- a/src/mixer/plugins/PulseMixerPlugin.cxx
+++ b/src/mixer/plugins/PulseMixerPlugin.cxx
@@ -51,7 +51,7 @@ public:
 		   double _volume_scale_factor)
 		:Mixer(pulse_mixer_plugin, _listener),
 		 output(_output),
-		 volume_scale_factor(_volume_scale_factor)
+		 volume_scale_factor(float(_volume_scale_factor))
 	{
 	}
 
@@ -175,7 +175,7 @@ parse_volume_scale_factor(const char *value) {
 	char *endptr;
 	float factor = ParseFloat(value, &endptr);
 
-	if (endptr == value || *endptr != '\0' || factor < 0.5 || factor > 5.0)
+	if (endptr == value || *endptr != '\0' || factor < 0.5f || factor > 5.0f)
 		throw FormatRuntimeError("\"%s\" is not a number in the "
 					 "range 0.5 to 5.0",
 					 value);
@@ -190,7 +190,7 @@ pulse_mixer_init(gcc_unused EventLoop &event_loop, AudioOutput &ao,
 {
 	PulseOutput &po = (PulseOutput &)ao;
 	float scale = parse_volume_scale_factor(block.GetBlockValue("scale_volume"));
-	PulseMixer *pm = new PulseMixer(po, listener, scale);
+	auto *pm = new PulseMixer(po, listener, (double)scale);
 
 	pulse_output_set_mixer(po, *pm);
 
@@ -216,7 +216,7 @@ PulseMixer::GetVolume()
 int
 PulseMixer::GetVolumeInternal()
 {
-	pa_volume_t max_pa_volume = volume_scale_factor * PA_VOLUME_NORM;
+	pa_volume_t max_pa_volume = pa_volume_t(volume_scale_factor * PA_VOLUME_NORM);
 	return online ?
 		(int)((100 * (pa_cvolume_avg(&volume) + 1)) / max_pa_volume)
 		: -1;
@@ -230,7 +230,7 @@ PulseMixer::SetVolume(unsigned new_volume)
 	if (!online)
 		throw std::runtime_error("disconnected");
 
-	pa_volume_t max_pa_volume = volume_scale_factor * PA_VOLUME_NORM;
+	pa_volume_t max_pa_volume = pa_volume_t(volume_scale_factor * PA_VOLUME_NORM);
 
 	struct pa_cvolume cvolume;
 	pa_cvolume_set(&cvolume, volume.channels,
diff --git a/src/mixer/plugins/SoftwareMixerPlugin.cxx b/src/mixer/plugins/SoftwareMixerPlugin.cxx
index 177c875d2..8105db537 100644
--- a/src/mixer/plugins/SoftwareMixerPlugin.cxx
+++ b/src/mixer/plugins/SoftwareMixerPlugin.cxx
@@ -22,8 +22,8 @@
 #include "filter/plugins/VolumeFilterPlugin.hxx"
 #include "pcm/Volume.hxx"
 
-#include <assert.h>
-#include <math.h>
+#include <cassert>
+#include <cmath>
 
 class SoftwareMixer final : public Mixer {
 	Filter *filter = nullptr;
@@ -70,13 +70,13 @@ PercentVolumeToSoftwareVolume(unsigned volume) noexcept
 {
 	assert(volume <= 100);
 
-	if (volume >= 100)
+	if (volume == 100)
 		return PCM_VOLUME_1;
 	else if (volume > 0)
-		return pcm_float_to_volume((exp(volume / 25.0) - 1) /
+		return pcm_float_to_volume((std::exp(volume / 25.0f) - 1) /
 					   (54.5981500331F - 1));
-	else
-		return 0;
+
+	return 0;
 }
 
 void
diff --git a/src/output/Source.cxx b/src/output/Source.cxx
index 7c5098d8e..27c7c362b 100644
--- a/src/output/Source.cxx
+++ b/src/output/Source.cxx
@@ -187,7 +187,7 @@ AudioOutputSource::FilterChunk(const MusicChunk &chunk)
 			   only if the mix ratio is non-negative; a
 			   negative mix ratio is a MixRamp special
 			   case */
-			mix_ratio = 1.0 - mix_ratio;
+			mix_ratio = 1.0f - mix_ratio;
 
 		void *dest = cross_fade_buffer.Get(other_data.size);
 		memcpy(dest, other_data.data, other_data.size);
diff --git a/src/pcm/FloatConvert.hxx b/src/pcm/FloatConvert.hxx
index 28f923c7a..17fcd27ce 100644
--- a/src/pcm/FloatConvert.hxx
+++ b/src/pcm/FloatConvert.hxx
@@ -53,7 +53,7 @@ struct IntegerToFloatSampleConvert {
 	typedef typename SrcTraits::value_type SV;
 	typedef typename DstTraits::value_type DV;
 
-	static constexpr DV factor = 1.0 / FloatToIntegerSampleConvert<F, Traits>::factor;
+	static constexpr DV factor = 1.0f / FloatToIntegerSampleConvert<F, Traits>::factor;
 	static_assert(factor > 0, "Wrong factor");
 
 	static constexpr DV Convert(SV src) noexcept {
diff --git a/src/pcm/PcmMix.cxx b/src/pcm/PcmMix.cxx
index bbb26d1c4..11d201c3e 100644
--- a/src/pcm/PcmMix.cxx
+++ b/src/pcm/PcmMix.cxx
@@ -26,6 +26,8 @@
 
 #include "PcmDither.cxx" // including the .cxx file to get inlined templates
 
+#include <cmath>
+
 #include <assert.h>
 
 template<SampleFormat F, class Traits=SampleTraits<F>>
@@ -221,7 +223,7 @@ pcm_mix(PcmDither &dither, void *buffer1, const void *buffer2, size_t size,
 	if (portion1 < 0)
 		return pcm_add(buffer1, buffer2, size, format);
 
-	s = sin(M_PI_2 * portion1);
+	s = std::sin((float)M_PI_2 * portion1);
 	s *= s;
 
 	int vol1 = lround(s * PCM_VOLUME_1S);
diff --git a/src/pcm/SoxrResampler.cxx b/src/pcm/SoxrResampler.cxx
index 411e79b43..2dcb507e0 100644
--- a/src/pcm/SoxrResampler.cxx
+++ b/src/pcm/SoxrResampler.cxx
@@ -122,7 +122,7 @@ SoxrPcmResampler::Open(AudioFormat &af, unsigned new_sample_rate)
 	ratio = float(new_sample_rate) / float(af.sample_rate);
 	FormatDebug(soxr_domain,
 		    "samplerate conversion ratio to %.2lf",
-		    ratio);
+		    double(ratio));
 
 	/* libsoxr works with floating point samples */
 	af.format = SampleFormat::FLOAT;
diff --git a/src/pcm/Volume.hxx b/src/pcm/Volume.hxx
index ddc6cb854..52a63d819 100644
--- a/src/pcm/Volume.hxx
+++ b/src/pcm/Volume.hxx
@@ -48,7 +48,7 @@ static constexpr int PCM_VOLUME_1S = PCM_VOLUME_1;
 static constexpr inline int
 pcm_float_to_volume(float volume) noexcept
 {
-	return volume * PCM_VOLUME_1 + 0.5;
+	return int(volume * PCM_VOLUME_1 + 0.5f);
 }
 
 static constexpr inline float
diff --git a/src/queue/PlaylistState.cxx b/src/queue/PlaylistState.cxx
index f57409de0..2e2ab3ec1 100644
--- a/src/queue/PlaylistState.cxx
+++ b/src/queue/PlaylistState.cxx
@@ -92,7 +92,8 @@ playlist_state_save(BufferedOutputStream &os, const struct playlist &playlist,
 	os.Format(PLAYLIST_STATE_FILE_CONSUME "%i\n", playlist.queue.consume);
 	os.Format(PLAYLIST_STATE_FILE_CROSSFADE "%i\n",
 		  (int)pc.GetCrossFade().count());
-	os.Format(PLAYLIST_STATE_FILE_MIXRAMPDB "%f\n", pc.GetMixRampDb());
+	os.Format(PLAYLIST_STATE_FILE_MIXRAMPDB "%f\n",
+		  (double)pc.GetMixRampDb());
 	os.Format(PLAYLIST_STATE_FILE_MIXRAMPDELAY "%f\n",
 		  pc.GetMixRampDelay().count());
 	os.Write(PLAYLIST_STATE_FILE_PLAYLIST_BEGIN "\n");