[PATCH] [UBUNTU:{include/sound, sound/pci/ymfpci}/] Fix PM and IEC958 output for ymfpci

crimsun at fungus.sh.nu crimsun at fungus.sh.nu
Sun Aug 13 23:07:11 UTC 2006


From 041d2cac3790f87a8fa8655f3d7e9ffa0f0a858c Mon Sep 17 00:00:00 2001
From: Daniel T. Chen <crimsun at garnish.localdomain>
Date: Sun, 13 Aug 2006 19:03:26 -0400
Subject: [PATCH] [UBUNTU:{include/sound,sound/pci/ymfpci}/] Fix PM and IEC958 output for ymfpci

UpstreamStatus: Added in upstream alsa-current git changesets:
		ded462356886e5f80f6a20b227f7e5cf7cfc5159 [http://www.kernel.org/git/?p=linux/kernel/git/perex/alsa-current.git;a=commitdiff_plain;h=ded462356886e5f80f6a20b227f7e5cf7cfc5159;hp=fb0700b4debbf45fb0465b40188bdc5396947bda],
		5a25c5cfd4f61f514decca3c4106210fb168ce19 [http://www.kernel.org/git/?p=linux/kernel/git/perex/alsa-current.git;a=commitdiff_plain;h=5a25c5cfd4f61f514decca3c4106210fb168ce19;hp=12aa757905d09b1dc2c1c3d0de3fa8f4c9726f2b]

Backport PM and IEC958 output fixes for ymfpci from alsa-current git.

Signed-off-by: Daniel T Chen <crimsun at ubuntu.com>
---
 include/sound/ymfpci.h         |   12 ++++++---
 sound/pci/ymfpci/ymfpci.c      |   11 +++++++-
 sound/pci/ymfpci/ymfpci_main.c |   53 +++++++++++++++++++++++++++-------------
 3 files changed, 53 insertions(+), 23 deletions(-)

diff --git a/include/sound/ymfpci.h b/include/sound/ymfpci.h
index c3bccbf..ee0a436 100644
--- a/include/sound/ymfpci.h
+++ b/include/sound/ymfpci.h
@@ -270,9 +270,10 @@ struct _snd_ymfpci_pcm {
 	snd_ymfpci_pcm_type_t type;
 	snd_pcm_substream_t *substream;
 	ymfpci_voice_t *voices[2];	/* playback only */
-	unsigned int running: 1;
-	unsigned int output_front: 1;
-	unsigned int output_rear: 1;
+	unsigned int running: 1,
+		     output_front: 1,
+		     output_rear: 1,
+		     swap_rear: 1;
 	unsigned int update_pcm_vol;
 	u32 period_size;		/* cached from runtime->period_size */
 	u32 buffer_size;		/* cached from runtime->buffer_size */
@@ -345,6 +346,7 @@ #endif
 	snd_kcontrol_t *spdif_pcm_ctl;
 	int mode_dup4ch;
 	int rear_opened;
+	int rear_swap;
 	int spdif_opened;
 	struct {
 		u16 left;
@@ -370,11 +372,13 @@ int snd_ymfpci_create(snd_card_t * card,
 		      ymfpci_t ** rcodec);
 void snd_ymfpci_free_gameport(ymfpci_t *chip);
 
+int snd_ymfpci_suspend(struct pci_dev *pci, pm_message_t state);
+int snd_ymfpci_resume(struct pci_dev *pci);
 int snd_ymfpci_pcm(ymfpci_t *chip, int device, snd_pcm_t **rpcm);
 int snd_ymfpci_pcm2(ymfpci_t *chip, int device, snd_pcm_t **rpcm);
 int snd_ymfpci_pcm_spdif(ymfpci_t *chip, int device, snd_pcm_t **rpcm);
 int snd_ymfpci_pcm_4ch(ymfpci_t *chip, int device, snd_pcm_t **rpcm);
-int snd_ymfpci_mixer(ymfpci_t *chip, int rear_switch);
+int snd_ymfpci_mixer(ymfpci_t *chip, int rear_switch, int rear_swap);
 int snd_ymfpci_timer(ymfpci_t *chip, int device);
 
 #endif /* __SOUND_YMFPCI_H */
diff --git a/sound/pci/ymfpci/ymfpci.c b/sound/pci/ymfpci/ymfpci.c
index d013237..0072036 100644
--- a/sound/pci/ymfpci/ymfpci.c
+++ b/sound/pci/ymfpci/ymfpci.c
@@ -49,6 +49,7 @@ #ifdef SUPPORT_JOYSTICK
 static long joystick_port[SNDRV_CARDS];
 #endif
 static int rear_switch[SNDRV_CARDS];
+static int rear_swap[SNDRV_CARDS] = { [0 ... (SNDRV_CARDS-1)] = 1 };
 
 module_param_array(index, int, NULL, 0444);
 MODULE_PARM_DESC(index, "Index value for the Yamaha DS-XG PCI soundcard.");
@@ -66,6 +67,8 @@ MODULE_PARM_DESC(joystick_port, "Joystic
 #endif
 module_param_array(rear_switch, bool, NULL, 0444);
 MODULE_PARM_DESC(rear_switch, "Enable shared rear/line-in switch");
+module_param_array(rear_swap, bool, NULL, 0444);
+MODULE_PARM_DESC(rear_swap, "Swap rear channels (must be enabled for correct IEC958 (S/PDIF)) output");
 
 static struct pci_device_id snd_ymfpci_ids[] = {
         { 0x1073, 0x0004, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0, },   /* YMF724 */
@@ -271,6 +274,7 @@ static int __devinit snd_card_ymfpci_pro
 	}
 	chip->fm_res = fm_res;
 	chip->mpu_res = mpu_res;
+	card->private_data = chip;
 	strcpy(card->driver, str);
 	sprintf(card->shortname, "Yamaha DS-XG (%s)", str);
 	sprintf(card->longname, "%s at 0x%lx, irq %i",
@@ -293,7 +297,7 @@ static int __devinit snd_card_ymfpci_pro
 		snd_card_free(card);
 		return err;
 	}
-	if ((err = snd_ymfpci_mixer(chip, rear_switch[dev])) < 0) {
+	if ((err = snd_ymfpci_mixer(chip, rear_switch[dev], rear_swap[dev])) < 0) {
 		snd_card_free(card);
 		return err;
 	}
@@ -347,7 +351,10 @@ static struct pci_driver driver = {
 	.id_table = snd_ymfpci_ids,
 	.probe = snd_card_ymfpci_probe,
 	.remove = __devexit_p(snd_card_ymfpci_remove),
-	SND_PCI_PM_CALLBACKS
+#ifdef CONFIG_PM
+	.suspend = snd_ymfpci_suspend,
+	.resume = snd_ymfpci_resume,
+#endif
 };
 
 static int __init alsa_card_ymfpci_init(void)
diff --git a/sound/pci/ymfpci/ymfpci_main.c b/sound/pci/ymfpci/ymfpci_main.c
index 88a43e0..2d92770 100644
--- a/sound/pci/ymfpci/ymfpci_main.c
+++ b/sound/pci/ymfpci/ymfpci_main.c
@@ -532,13 +532,24 @@ static void snd_ymfpci_pcm_init_voice(ym
 			}
 		}
 		if (ypcm->output_rear) {
-			if (use_left) {
-				bank->eff2_gain =
-				bank->eff2_gain_end = vol_left;
-			}
-			if (use_right) {
-				bank->eff3_gain =
-				bank->eff3_gain_end = vol_right;
+			if (!ypcm->swap_rear) {
+				if (use_left) {
+					bank->eff2_gain =
+					bank->eff2_gain_end = vol_left;
+				}
+				if (use_right) {
+					bank->eff3_gain =
+					bank->eff3_gain_end = vol_right;
+				}
+			} else {
+				if (use_left) {
+					bank->eff3_gain =
+					bank->eff3_gain_end = vol_left;
+				}
+				if (use_right) {
+					bank->eff2_gain =
+					bank->eff2_gain_end = vol_right;
+				}
 			}
 		}
 	}
@@ -890,6 +901,7 @@ static int snd_ymfpci_playback_open(snd_
 	ypcm = runtime->private_data;
 	ypcm->output_front = 1;
 	ypcm->output_rear = chip->mode_dup4ch ? 1 : 0;
+	ypcm->swap_rear = chip->rear_swap;
 	spin_lock_irq(&chip->reg_lock);
 	if (ypcm->output_rear) {
 		ymfpci_open_extension(chip);
@@ -1760,7 +1772,7 @@ static void snd_ymfpci_mixer_free_ac97(a
 	chip->ac97 = NULL;
 }
 
-int __devinit snd_ymfpci_mixer(ymfpci_t *chip, int rear_switch)
+int __devinit snd_ymfpci_mixer(ymfpci_t *chip, int rear_switch, int rear_swap)
 {
 	ac97_template_t ac97;
 	snd_kcontrol_t *kctl;
@@ -1772,6 +1784,7 @@ int __devinit snd_ymfpci_mixer(ymfpci_t 
 		.read = snd_ymfpci_codec_read,
 	};
 
+	chip->rear_swap = rear_swap;
 	if ((err = snd_ac97_bus(chip->card, 0, &ops, chip, &chip->ac97_bus)) < 0)
 		return err;
 	chip->ac97_bus->private_free = snd_ymfpci_mixer_free_ac97_bus;
@@ -2203,11 +2216,13 @@ static int saved_regs_index[] = {
 };
 #define YDSXGR_NUM_SAVED_REGS	ARRAY_SIZE(saved_regs_index)
 
-static int snd_ymfpci_suspend(snd_card_t *card, pm_message_t state)
+int snd_ymfpci_suspend(struct pci_dev *pci, pm_message_t state)
 {
-	ymfpci_t *chip = card->pm_private_data;
+	snd_card_t *card = pci_get_drvdata(pci);
+	ymfpci_t *chip = card->private_data;
 	unsigned int i;
 	
+	snd_power_change_state(card, SNDRV_CTL_POWER_D3hot);
 	snd_pcm_suspend_all(chip->pcm);
 	snd_pcm_suspend_all(chip->pcm2);
 	snd_pcm_suspend_all(chip->pcm_spdif);
@@ -2218,18 +2233,21 @@ static int snd_ymfpci_suspend(snd_card_t
 	chip->saved_ydsxgr_mode = snd_ymfpci_readl(chip, YDSXGR_MODE);
 	snd_ymfpci_writel(chip, YDSXGR_NATIVEDACOUTVOL, 0);
 	snd_ymfpci_disable_dsp(chip);
-	pci_disable_device(chip->pci);
+	pci_disable_device(pci);
+	pci_save_state(pci);
 	return 0;
 }
 
-static int snd_ymfpci_resume(snd_card_t *card)
+int snd_ymfpci_resume(struct pci_dev *pci)
 {
-	ymfpci_t *chip = card->pm_private_data;
+	snd_card_t *card = pci_get_drvdata(pci);
+	ymfpci_t *chip = card->private_data;
 	unsigned int i;
 
-	pci_enable_device(chip->pci);
-	pci_set_master(chip->pci);
-	snd_ymfpci_aclink_reset(chip->pci);
+	pci_restore_state(pci);
+	pci_enable_device(pci);
+	pci_set_master(pci);
+	snd_ymfpci_aclink_reset(pci);
 	snd_ymfpci_codec_ready(chip, 0);
 	snd_ymfpci_download_image(chip);
 	udelay(100);
@@ -2246,6 +2264,7 @@ static int snd_ymfpci_resume(snd_card_t 
 		chip->active_bank = snd_ymfpci_readl(chip, YDSXGR_CTRLSELECT);
 		spin_unlock_irq(&chip->reg_lock);
 	}
+	snd_power_change_state(card, SNDRV_CTL_POWER_D0);
 	return 0;
 }
 #endif /* CONFIG_PM */
@@ -2313,6 +2332,7 @@ int __devinit snd_ymfpci_create(snd_card
 		return -EIO;
 	}
 
+	chip->rear_swap = 1;
 	if ((err = snd_ymfpci_ac3_init(chip)) < 0) {
 		snd_ymfpci_free(chip);
 		return err;
@@ -2324,7 +2344,6 @@ #ifdef CONFIG_PM
 		snd_ymfpci_free(chip);
 		return -ENOMEM;
 	}
-	snd_card_set_pm_callback(card, snd_ymfpci_suspend, snd_ymfpci_resume, chip);
 #endif
 
 	if ((err = snd_device_new(card, SNDRV_DEV_LOWLEVEL, chip, &ops)) < 0) {
-- 
1.4.1

-- 
Daniel T. Chen            crimsun at ubuntu.com
GPG key:  0xC88ABDA3
-------------- next part --------------
A non-text attachment was scrubbed...
Name: not available
Type: application/pgp-signature
Size: 189 bytes
Desc: not available
URL: <https://lists.ubuntu.com/archives/kernel-team/attachments/20060813/cef77487/attachment.sig>


More information about the kernel-team mailing list