[ALSA] atiixp - Add a parameter ac97_quirk
Add an option to specify the AC'97 codec instead of probing. This is a fix for bugzilla #7467. Signed-off-by: Dan Carpenter <error27@gmail.com> Signed-off-by: Takashi Iwai <tiwai@suse.de> Signed-off-by: Jaroslav Kysela <perex@suse.cz>
This commit is contained in:
committed by
Jaroslav Kysela
parent
ddc2cec4db
commit
14e1d357e4
@@ -242,6 +242,12 @@ Prior to version 0.9.0rc4 options had a 'snd_' prefix. This was removed.
|
|||||||
ac97_clock - AC'97 clock (default = 48000)
|
ac97_clock - AC'97 clock (default = 48000)
|
||||||
ac97_quirk - AC'97 workaround for strange hardware
|
ac97_quirk - AC'97 workaround for strange hardware
|
||||||
See "AC97 Quirk Option" section below.
|
See "AC97 Quirk Option" section below.
|
||||||
|
ac97_codec - Workaround to specify which AC'97 codec
|
||||||
|
instead of probing. If this works for you
|
||||||
|
file a bug with your `lspci -vn` output.
|
||||||
|
-2 -- Force probing.
|
||||||
|
-1 -- Default behavior.
|
||||||
|
0-2 -- Use the specified codec.
|
||||||
spdif_aclink - S/PDIF transfer over AC-link (default = 1)
|
spdif_aclink - S/PDIF transfer over AC-link (default = 1)
|
||||||
|
|
||||||
This module supports one card and autoprobe.
|
This module supports one card and autoprobe.
|
||||||
|
@@ -45,6 +45,7 @@ static char *id = SNDRV_DEFAULT_STR1; /* ID for this card */
|
|||||||
static int ac97_clock = 48000;
|
static int ac97_clock = 48000;
|
||||||
static char *ac97_quirk;
|
static char *ac97_quirk;
|
||||||
static int spdif_aclink = 1;
|
static int spdif_aclink = 1;
|
||||||
|
static int ac97_codec = -1;
|
||||||
|
|
||||||
module_param(index, int, 0444);
|
module_param(index, int, 0444);
|
||||||
MODULE_PARM_DESC(index, "Index value for ATI IXP controller.");
|
MODULE_PARM_DESC(index, "Index value for ATI IXP controller.");
|
||||||
@@ -54,6 +55,8 @@ module_param(ac97_clock, int, 0444);
|
|||||||
MODULE_PARM_DESC(ac97_clock, "AC'97 codec clock (default 48000Hz).");
|
MODULE_PARM_DESC(ac97_clock, "AC'97 codec clock (default 48000Hz).");
|
||||||
module_param(ac97_quirk, charp, 0444);
|
module_param(ac97_quirk, charp, 0444);
|
||||||
MODULE_PARM_DESC(ac97_quirk, "AC'97 workaround for strange hardware.");
|
MODULE_PARM_DESC(ac97_quirk, "AC'97 workaround for strange hardware.");
|
||||||
|
module_param(ac97_codec, int, 0444);
|
||||||
|
MODULE_PARM_DESC(ac97_codec, "Specify codec instead of probing.");
|
||||||
module_param(spdif_aclink, bool, 0444);
|
module_param(spdif_aclink, bool, 0444);
|
||||||
MODULE_PARM_DESC(spdif_aclink, "S/PDIF over AC-link.");
|
MODULE_PARM_DESC(spdif_aclink, "S/PDIF over AC-link.");
|
||||||
|
|
||||||
@@ -293,6 +296,22 @@ static struct pci_device_id snd_atiixp_ids[] = {
|
|||||||
|
|
||||||
MODULE_DEVICE_TABLE(pci, snd_atiixp_ids);
|
MODULE_DEVICE_TABLE(pci, snd_atiixp_ids);
|
||||||
|
|
||||||
|
struct atiixp_quirk {
|
||||||
|
unsigned short subvendor;
|
||||||
|
unsigned short subdevice;
|
||||||
|
const char *name;
|
||||||
|
int ac97_codec;
|
||||||
|
};
|
||||||
|
|
||||||
|
static struct atiixp_quirk atiixp_quirks[] __devinitdata = {
|
||||||
|
{
|
||||||
|
.subvendor = 0x15bd,
|
||||||
|
.subdevice = 0x3100,
|
||||||
|
.name = "DFI RS482",
|
||||||
|
.ac97_codec = 0,
|
||||||
|
},
|
||||||
|
{ .subvendor = 0 } /* terminator */
|
||||||
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* lowlevel functions
|
* lowlevel functions
|
||||||
@@ -553,11 +572,37 @@ static int snd_atiixp_aclink_down(struct atiixp *chip)
|
|||||||
ATI_REG_ISR_CODEC2_NOT_READY)
|
ATI_REG_ISR_CODEC2_NOT_READY)
|
||||||
#define CODEC_CHECK_BITS (ALL_CODEC_NOT_READY|ATI_REG_ISR_NEW_FRAME)
|
#define CODEC_CHECK_BITS (ALL_CODEC_NOT_READY|ATI_REG_ISR_NEW_FRAME)
|
||||||
|
|
||||||
|
static int ac97_probing_bugs(struct pci_dev *pci)
|
||||||
|
{
|
||||||
|
int i = 0;
|
||||||
|
|
||||||
|
while (atiixp_quirks[i].subvendor) {
|
||||||
|
if (pci->subsystem_vendor == atiixp_quirks[i].subvendor &&
|
||||||
|
pci->subsystem_device == atiixp_quirks[i].subdevice) {
|
||||||
|
printk(KERN_INFO "Atiixp quirk for %s. "
|
||||||
|
"Forcing codec %d\n", atiixp_quirks[i].name,
|
||||||
|
atiixp_quirks[i].ac97_codec);
|
||||||
|
return atiixp_quirks[i].ac97_codec;
|
||||||
|
}
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
/* this hardware doesn't need workarounds. Probe for codec */
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
static int snd_atiixp_codec_detect(struct atiixp *chip)
|
static int snd_atiixp_codec_detect(struct atiixp *chip)
|
||||||
{
|
{
|
||||||
int timeout;
|
int timeout;
|
||||||
|
|
||||||
chip->codec_not_ready_bits = 0;
|
chip->codec_not_ready_bits = 0;
|
||||||
|
if (ac97_codec == -1)
|
||||||
|
ac97_codec = ac97_probing_bugs(chip->pci);
|
||||||
|
if (ac97_codec >= 0) {
|
||||||
|
chip->codec_not_ready_bits |=
|
||||||
|
CODEC_CHECK_BITS ^ (1 << (ac97_codec + 10));
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
atiixp_write(chip, IER, CODEC_CHECK_BITS);
|
atiixp_write(chip, IER, CODEC_CHECK_BITS);
|
||||||
/* wait for the interrupts */
|
/* wait for the interrupts */
|
||||||
timeout = 50;
|
timeout = 50;
|
||||||
|
Reference in New Issue
Block a user