diff mbox series

[1/9] ALSA: emu10k1: split off E-MU fallback clock from clock source

Message ID 20230612191325.1315854-2-oswald.buddenhagen@gmx.de
State Accepted
Commit 1359886227e52c27c0a230769f3be4c486e36299
Headers show
Series ALSA: emu10k1: improvements related to the switchable word clock of E-MU cards | expand

Commit Message

Oswald Buddenhagen June 12, 2023, 7:13 p.m. UTC
So far, we set the fallback as a side effect of setting the source. But
the fallback makes no sense at all when an internal clock is selected.
Defaulting to 48k for S/PDIF & ADAT makes sense, but as that is the
global default and we're not changing it automatically any more, it's
just fine to leave it entirely to the explicit setting.

This changes the name of the pre-existing control to something more
appropriate (regardless of the split), so users will need to adjust
their mixer settings.

Signed-off-by: Oswald Buddenhagen <oswald.buddenhagen@gmx.de>
---
 include/sound/emu10k1.h          |  3 +-
 sound/pci/emu10k1/emu10k1_main.c |  3 +-
 sound/pci/emu10k1/emumixer.c     | 89 +++++++++++++++++++++++---------
 sound/pci/emu10k1/emupcm.c       |  4 +-
 4 files changed, 72 insertions(+), 27 deletions(-)
diff mbox series

Patch

diff --git a/include/sound/emu10k1.h b/include/sound/emu10k1.h
index cc0151e7c828..59e79ea1f75e 100644
--- a/include/sound/emu10k1.h
+++ b/include/sound/emu10k1.h
@@ -1668,7 +1668,8 @@  struct snd_emu1010 {
 	unsigned char input_source[NUM_INPUT_DESTS];
 	unsigned int adc_pads; /* bit mask */
 	unsigned int dac_pads; /* bit mask */
-	unsigned int internal_clock; /* 44100 or 48000 */
+	unsigned int clock_source;
+	unsigned int clock_fallback;
 	unsigned int optical_in; /* 0:SPDIF, 1:ADAT */
 	unsigned int optical_out; /* 0:SPDIF, 1:ADAT */
 	struct delayed_work firmware_work;
diff --git a/sound/pci/emu10k1/emu10k1_main.c b/sound/pci/emu10k1/emu10k1_main.c
index 65207ef689cb..2aa11d70e285 100644
--- a/sound/pci/emu10k1/emu10k1_main.c
+++ b/sound/pci/emu10k1/emu10k1_main.c
@@ -900,7 +900,8 @@  static int snd_emu10k1_emu1010_init(struct snd_emu10k1 *emu)
 	/* IRQ Enable: All off */
 	snd_emu1010_fpga_write(emu, EMU_HANA_IRQ_ENABLE, 0x00);
 
-	emu->emu1010.internal_clock = 1; /* 48000 */
+	emu->emu1010.clock_source = 1;  /* 48000 */
+	emu->emu1010.clock_fallback = 1;  /* 48000 */
 	/* Default WCLK set to 48kHz. */
 	snd_emu1010_fpga_write(emu, EMU_HANA_DEFCLOCK, EMU_HANA_DEFCLOCK_48K);
 	/* Word Clock source, Internal 48kHz x1 */
diff --git a/sound/pci/emu10k1/emumixer.c b/sound/pci/emu10k1/emumixer.c
index 20a0b3afc8a5..5b50d9c07a60 100644
--- a/sound/pci/emu10k1/emumixer.c
+++ b/sound/pci/emu10k1/emumixer.c
@@ -888,46 +888,44 @@  static const struct snd_emu1010_pads_info emu1010_pads_info[] = {
 };
 
 
-static int snd_emu1010_internal_clock_info(struct snd_kcontrol *kcontrol,
+static int snd_emu1010_clock_source_info(struct snd_kcontrol *kcontrol,
 					  struct snd_ctl_elem_info *uinfo)
 {
 	static const char * const texts[4] = {
 		"44100", "48000", "SPDIF", "ADAT"
 	};
 		
 	return snd_ctl_enum_info(uinfo, 1, 4, texts);
 }
 
-static int snd_emu1010_internal_clock_get(struct snd_kcontrol *kcontrol,
+static int snd_emu1010_clock_source_get(struct snd_kcontrol *kcontrol,
 					struct snd_ctl_elem_value *ucontrol)
 {
 	struct snd_emu10k1 *emu = snd_kcontrol_chip(kcontrol);
 
-	ucontrol->value.enumerated.item[0] = emu->emu1010.internal_clock;
+	ucontrol->value.enumerated.item[0] = emu->emu1010.clock_source;
 	return 0;
 }
 
-static int snd_emu1010_internal_clock_put(struct snd_kcontrol *kcontrol,
+static int snd_emu1010_clock_source_put(struct snd_kcontrol *kcontrol,
 					struct snd_ctl_elem_value *ucontrol)
 {
 	struct snd_emu10k1 *emu = snd_kcontrol_chip(kcontrol);
 	unsigned int val;
 	int change = 0;
 
 	val = ucontrol->value.enumerated.item[0] ;
 	/* Limit: uinfo->value.enumerated.items = 4; */
 	if (val >= 4)
 		return -EINVAL;
-	change = (emu->emu1010.internal_clock != val);
+	change = (emu->emu1010.clock_source != val);
 	if (change) {
-		emu->emu1010.internal_clock = val;
+		emu->emu1010.clock_source = val;
 		switch (val) {
 		case 0:
 			/* 44100 */
 			/* Mute all */
 			snd_emu1010_fpga_write(emu, EMU_HANA_UNMUTE, EMU_MUTE );
-			/* Default fallback clock 44.1kHz */
-			snd_emu1010_fpga_write(emu, EMU_HANA_DEFCLOCK, EMU_HANA_DEFCLOCK_44_1K );
 			/* Word Clock source, Internal 44.1kHz x1 */
 			snd_emu1010_fpga_write(emu, EMU_HANA_WCLOCK,
 			EMU_HANA_WCLOCK_INT_44_1K | EMU_HANA_WCLOCK_1X );
@@ -943,8 +941,6 @@  static int snd_emu1010_internal_clock_put(struct snd_kcontrol *kcontrol,
 			/* 48000 */
 			/* Mute all */
 			snd_emu1010_fpga_write(emu, EMU_HANA_UNMUTE, EMU_MUTE );
-			/* Default fallback clock 48kHz */
-			snd_emu1010_fpga_write(emu, EMU_HANA_DEFCLOCK, EMU_HANA_DEFCLOCK_48K );
 			/* Word Clock source, Internal 48kHz x1 */
 			snd_emu1010_fpga_write(emu, EMU_HANA_WCLOCK,
 				EMU_HANA_WCLOCK_INT_48K | EMU_HANA_WCLOCK_1X );
@@ -960,8 +956,6 @@  static int snd_emu1010_internal_clock_put(struct snd_kcontrol *kcontrol,
 		case 2: /* Take clock from S/PDIF IN */
 			/* Mute all */
 			snd_emu1010_fpga_write(emu, EMU_HANA_UNMUTE, EMU_MUTE );
-			/* Default fallback clock 48kHz */
-			snd_emu1010_fpga_write(emu, EMU_HANA_DEFCLOCK, EMU_HANA_DEFCLOCK_48K );
 			/* Word Clock source, sync to S/PDIF input */
 			snd_emu1010_fpga_write(emu, EMU_HANA_WCLOCK,
 				EMU_HANA_WCLOCK_HANA_SPDIF_IN | EMU_HANA_WCLOCK_1X );
@@ -979,8 +973,6 @@  static int snd_emu1010_internal_clock_put(struct snd_kcontrol *kcontrol,
 			/* Take clock from ADAT IN */
 			/* Mute all */
 			snd_emu1010_fpga_write(emu, EMU_HANA_UNMUTE, EMU_MUTE );
-			/* Default fallback clock 48kHz */
-			snd_emu1010_fpga_write(emu, EMU_HANA_DEFCLOCK, EMU_HANA_DEFCLOCK_48K );
 			/* Word Clock source, sync to ADAT input */
 			snd_emu1010_fpga_write(emu, EMU_HANA_WCLOCK,
 				EMU_HANA_WCLOCK_HANA_ADAT_IN | EMU_HANA_WCLOCK_1X );
@@ -999,15 +991,62 @@  static int snd_emu1010_internal_clock_put(struct snd_kcontrol *kcontrol,
         return change;
 }
 
-static const struct snd_kcontrol_new snd_emu1010_internal_clock =
+static const struct snd_kcontrol_new snd_emu1010_clock_source =
 {
-	.access =	SNDRV_CTL_ELEM_ACCESS_READWRITE,
-	.iface =        SNDRV_CTL_ELEM_IFACE_MIXER,
-	.name =         "Clock Internal Rate",
-	.count =	1,
-	.info =         snd_emu1010_internal_clock_info,
-	.get =          snd_emu1010_internal_clock_get,
-	.put =          snd_emu1010_internal_clock_put
+	.access = SNDRV_CTL_ELEM_ACCESS_READWRITE,
+	.iface = SNDRV_CTL_ELEM_IFACE_MIXER,
+	.name = "Clock Source",
+	.count = 1,
+	.info = snd_emu1010_clock_source_info,
+	.get = snd_emu1010_clock_source_get,
+	.put = snd_emu1010_clock_source_put
+};
+
+static int snd_emu1010_clock_fallback_info(struct snd_kcontrol *kcontrol,
+					  struct snd_ctl_elem_info *uinfo)
+{
+	static const char * const texts[2] = {
+		"44100", "48000"
+	};
+
+	return snd_ctl_enum_info(uinfo, 1, 2, texts);
+}
+
+static int snd_emu1010_clock_fallback_get(struct snd_kcontrol *kcontrol,
+					  struct snd_ctl_elem_value *ucontrol)
+{
+	struct snd_emu10k1 *emu = snd_kcontrol_chip(kcontrol);
+
+	ucontrol->value.enumerated.item[0] = emu->emu1010.clock_fallback;
+	return 0;
+}
+
+static int snd_emu1010_clock_fallback_put(struct snd_kcontrol *kcontrol,
+					  struct snd_ctl_elem_value *ucontrol)
+{
+	struct snd_emu10k1 *emu = snd_kcontrol_chip(kcontrol);
+	unsigned int val = ucontrol->value.enumerated.item[0];
+	int change;
+
+	if (val >= 2)
+		return -EINVAL;
+	change = (emu->emu1010.clock_fallback != val);
+	if (change) {
+		emu->emu1010.clock_fallback = val;
+		snd_emu1010_fpga_write(emu, EMU_HANA_DEFCLOCK, 1 - val);
+	}
+	return change;
+}
+
+static const struct snd_kcontrol_new snd_emu1010_clock_fallback =
+{
+	.access = SNDRV_CTL_ELEM_ACCESS_READWRITE,
+	.iface = SNDRV_CTL_ELEM_IFACE_MIXER,
+	.name = "Clock Fallback",
+	.count = 1,
+	.info = snd_emu1010_clock_fallback_info,
+	.get = snd_emu1010_clock_fallback_get,
+	.put = snd_emu1010_clock_fallback_put
 };
 
 static int snd_emu1010_optical_out_info(struct snd_kcontrol *kcontrol,
@@ -2297,7 +2336,11 @@  int snd_emu10k1_mixer(struct snd_emu10k1 *emu,
 		snd_emu1010_apply_sources(emu);
 
 		err = snd_ctl_add(card,
-			snd_ctl_new1(&snd_emu1010_internal_clock, emu));
+			snd_ctl_new1(&snd_emu1010_clock_source, emu));
+		if (err < 0)
+			return err;
+		err = snd_ctl_add(card,
+			snd_ctl_new1(&snd_emu1010_clock_fallback, emu));
 		if (err < 0)
 			return err;
 
diff --git a/sound/pci/emu10k1/emupcm.c b/sound/pci/emu10k1/emupcm.c
index 550caefa0ce4..fab537788587 100644
--- a/sound/pci/emu10k1/emupcm.c
+++ b/sound/pci/emu10k1/emupcm.c
@@ -1185,7 +1185,7 @@  static int snd_emu10k1_playback_open(struct snd_pcm_substream *substream)
 		kfree(epcm);
 		return err;
 	}
-	if (emu->card_capabilities->emu_model && emu->emu1010.internal_clock == 0)
+	if (emu->card_capabilities->emu_model && emu->emu1010.clock_source == 0)
 		sample_rate = 44100;
 	else
 		sample_rate = 48000;
@@ -1335,7 +1335,7 @@  static int snd_emu10k1_capture_efx_open(struct snd_pcm_substream *substream)
 		 * but we don't exceed 16 channels anyway.
 		 */
 #if 1
-		switch (emu->emu1010.internal_clock) {
+		switch (emu->emu1010.clock_source) {
 		case 0:
 			/* For 44.1kHz */
 			runtime->hw.rates = SNDRV_PCM_RATE_44100;