Commit ab3225bc authored by Jaroslav Kysela's avatar Jaroslav Kysela

ALSA CVS update

D:2003/07/30 15:39:38
A:Takashi Iwai <tiwai@suse.de>
F:pci/intel8x0.c:1.86->1.87 
L:- improved the probe/resume function.
L:  check only the valid codec bits in chip_init() during resume.
parent c7d96eae
...@@ -523,6 +523,19 @@ static void iaputword(intel8x0_t *chip, u32 offset, u16 val) ...@@ -523,6 +523,19 @@ static void iaputword(intel8x0_t *chip, u32 offset, u16 val)
/* /*
* access to AC97 codec via normal i/o (for ICH and SIS7012) * access to AC97 codec via normal i/o (for ICH and SIS7012)
*/ */
/* return the GLOB_STA bit for the corresponding codec */
static unsigned int get_ich_codec_bit(intel8x0_t *chip, unsigned int codec)
{
static unsigned int codec_bit[3] = {
ICH_PCR, ICH_SCR, ICH_TCR
};
snd_assert(codec < 3, return ICH_PCR);
if (chip->device_type == DEVICE_INTEL_ICH4)
codec = chip->ac97_sdin[codec];
return codec_bit[codec];
}
static int snd_intel8x0_codec_semaphore(intel8x0_t *chip, unsigned int codec) static int snd_intel8x0_codec_semaphore(intel8x0_t *chip, unsigned int codec)
{ {
int time; int time;
...@@ -534,19 +547,7 @@ static int snd_intel8x0_codec_semaphore(intel8x0_t *chip, unsigned int codec) ...@@ -534,19 +547,7 @@ static int snd_intel8x0_codec_semaphore(intel8x0_t *chip, unsigned int codec)
/* so we check any */ /* so we check any */
codec = ICH_PCR | ICH_SCR | ICH_TCR; codec = ICH_PCR | ICH_SCR | ICH_TCR;
} else { } else {
if (chip->device_type == DEVICE_INTEL_ICH4) { codec = get_ich_codec_bit(chip, codec);
switch (chip->ac97_sdin[codec]) {
case 0: codec = ICH_PCR; break;
case 1: codec = ICH_SCR; break;
case 2: codec = ICH_TCR; break;
}
} else {
switch (codec) {
case 0: codec = ICH_PCR; break;
case 1: codec = ICH_SCR; break;
case 2: codec = ICH_TCR; break;
}
}
} }
/* codec ready ? */ /* codec ready ? */
...@@ -1731,9 +1732,14 @@ static int __devinit snd_intel8x0_mixer(intel8x0_t *chip, int ac97_clock) ...@@ -1731,9 +1732,14 @@ static int __devinit snd_intel8x0_mixer(intel8x0_t *chip, int ac97_clock)
} }
} }
ac97.pci = chip->pci; ac97.pci = chip->pci;
if ((err = snd_ac97_mixer(chip->card, &ac97, &x97)) < 0) if ((err = snd_ac97_mixer(chip->card, &ac97, &x97)) < 0) {
/* clear the cold-reset bit for the next chance */
if (chip->device_type != DEVICE_ALI)
iputdword(chip, ICHREG(GLOB_CNT), igetdword(chip, ICHREG(GLOB_CNT)) & ~ICH_AC97COLD);
return err; return err;
}
chip->ac97[0] = x97; chip->ac97[0] = x97;
/* tune up the primary codec */
snd_ac97_tune_hardware(chip->ac97[0], ac97_quirks); snd_ac97_tune_hardware(chip->ac97[0], ac97_quirks);
/* the following three entries are common among all devices */ /* the following three entries are common among all devices */
chip->ichd[ICHD_PCMOUT].ac97 = x97; chip->ichd[ICHD_PCMOUT].ac97 = x97;
...@@ -1886,7 +1892,7 @@ static void do_ali_reset(intel8x0_t *chip) ...@@ -1886,7 +1892,7 @@ static void do_ali_reset(intel8x0_t *chip)
schedule_timeout(1);\ schedule_timeout(1);\
} while (0) } while (0)
static int snd_intel8x0_ich_chip_init(intel8x0_t *chip) static int snd_intel8x0_ich_chip_init(intel8x0_t *chip, int probing)
{ {
unsigned long end_time; unsigned long end_time;
unsigned int cnt, status, nstatus; unsigned int cnt, status, nstatus;
...@@ -1915,49 +1921,55 @@ static int snd_intel8x0_ich_chip_init(intel8x0_t *chip) ...@@ -1915,49 +1921,55 @@ static int snd_intel8x0_ich_chip_init(intel8x0_t *chip)
return -EIO; return -EIO;
__ok: __ok:
/* wait for any codec ready status. if (probing) {
* Once it becomes ready it should remain ready /* wait for any codec ready status.
* as long as we do not disable the ac97 link. * Once it becomes ready it should remain ready
*/ * as long as we do not disable the ac97 link.
end_time = jiffies + HZ; */
do { end_time = jiffies + HZ;
status = igetdword(chip, ICHREG(GLOB_STA)) & (ICH_PCR | ICH_SCR | ICH_TCR); do {
if (status) status = igetdword(chip, ICHREG(GLOB_STA)) & (ICH_PCR | ICH_SCR | ICH_TCR);
goto __ok1; if (status)
do_delay(chip); break;
} while (time_after_eq(end_time, jiffies)); do_delay(chip);
snd_printk(KERN_ERR "codec_ready: codec is not ready [0x%x]\n", igetdword(chip, ICHREG(GLOB_STA))); } while (time_after_eq(end_time, jiffies));
return -EIO; if (! status) {
/* no codec is found */
__ok1: snd_printk(KERN_ERR "codec_ready: codec is not ready [0x%x]\n", igetdword(chip, ICHREG(GLOB_STA)));
if (status == (ICH_PCR | ICH_SCR | ICH_TCR)) return -EIO;
goto __ok3;
/* wait for other codecs ready status. No secondary codecs? , ok */
end_time = jiffies + HZ / 4;
do {
nstatus = igetdword(chip, ICHREG(GLOB_STA)) & (ICH_PCR | ICH_SCR | ICH_TCR);
if (nstatus != status) {
status = nstatus;
goto __ok2;
} }
do_delay(chip);
} while (time_after_eq(end_time, jiffies));
__ok2: if (chip->device_type == DEVICE_INTEL_ICH4)
if (status == (ICH_PCR | ICH_SCR | ICH_TCR)) /* ICH4 can have three codecs */
goto __ok3; nstatus = ICH_PCR | ICH_SCR | ICH_TCR;
/* wait for other codecs ready status. No other secondary codecs? , ok */ else
/* end_time is not initialized here */ /* others up to two codecs */
do { nstatus = ICH_PCR | ICH_SCR;
nstatus = igetdword(chip, ICHREG(GLOB_STA)) & (ICH_PCR | ICH_SCR | ICH_TCR);
if (nstatus != status) { /* wait for other codecs ready status. */
status = nstatus; end_time = jiffies + HZ / 4;
goto __ok2; while (status != nstatus && time_after_eq(end_time, jiffies)) {
do_delay(chip);
status |= igetdword(chip, ICHREG(GLOB_STA)) & nstatus;
} }
do_delay(chip);
} while (time_after_eq(end_time, jiffies));
__ok3: } else {
/* resume phase */
int i;
status = 0;
for (i = 0; i < 3; i++)
if (chip->ac97[i])
status |= get_ich_codec_bit(chip, i);
/* wait until all the probed codecs are ready */
end_time = jiffies + HZ;
do {
nstatus = igetdword(chip, ICHREG(GLOB_STA)) & (ICH_PCR | ICH_SCR | ICH_TCR);
if (status == nstatus)
break;
do_delay(chip);
} while (time_after_eq(end_time, jiffies));
}
if (chip->device_type == DEVICE_SIS) { if (chip->device_type == DEVICE_SIS) {
/* unmute the output on SIS7012 */ /* unmute the output on SIS7012 */
iputword(chip, 0x4c, igetword(chip, 0x4c) | 1); iputword(chip, 0x4c, igetword(chip, 0x4c) | 1);
...@@ -1972,7 +1984,7 @@ static int snd_intel8x0_ich_chip_init(intel8x0_t *chip) ...@@ -1972,7 +1984,7 @@ static int snd_intel8x0_ich_chip_init(intel8x0_t *chip)
return 0; return 0;
} }
static int snd_intel8x0_ali_chip_init(intel8x0_t *chip) static int snd_intel8x0_ali_chip_init(intel8x0_t *chip, int probing)
{ {
u32 reg; u32 reg;
int i = 0; int i = 0;
...@@ -1991,7 +2003,8 @@ static int snd_intel8x0_ali_chip_init(intel8x0_t *chip) ...@@ -1991,7 +2003,8 @@ static int snd_intel8x0_ali_chip_init(intel8x0_t *chip)
do_delay(chip); do_delay(chip);
} }
snd_printk(KERN_ERR "AC'97 reset failed.\n"); snd_printk(KERN_ERR "AC'97 reset failed.\n");
return -EIO; if (probing)
return -EIO;
__ok: __ok:
for (i = 0; i < HZ / 2; i++) { for (i = 0; i < HZ / 2; i++) {
...@@ -2006,17 +2019,17 @@ static int snd_intel8x0_ali_chip_init(intel8x0_t *chip) ...@@ -2006,17 +2019,17 @@ static int snd_intel8x0_ali_chip_init(intel8x0_t *chip)
return 0; return 0;
} }
static int snd_intel8x0_chip_init(intel8x0_t *chip) static int snd_intel8x0_chip_init(intel8x0_t *chip, int probing)
{ {
unsigned int i; unsigned int i;
int err; int err;
if (chip->device_type != DEVICE_ALI) { if (chip->device_type != DEVICE_ALI) {
if ((err = snd_intel8x0_ich_chip_init(chip)) < 0) if ((err = snd_intel8x0_ich_chip_init(chip, probing)) < 0)
return err; return err;
iagetword(chip, 0); /* clear semaphore flag */ iagetword(chip, 0); /* clear semaphore flag */
} else { } else {
if ((err = snd_intel8x0_ali_chip_init(chip)) < 0) if ((err = snd_intel8x0_ali_chip_init(chip, probing)) < 0)
return err; return err;
} }
...@@ -2104,7 +2117,7 @@ static void intel8x0_resume(intel8x0_t *chip) ...@@ -2104,7 +2117,7 @@ static void intel8x0_resume(intel8x0_t *chip)
pci_enable_device(chip->pci); pci_enable_device(chip->pci);
pci_set_master(chip->pci); pci_set_master(chip->pci);
snd_intel8x0_chip_init(chip); snd_intel8x0_chip_init(chip, 0);
for (i = 0; i < 3; i++) for (i = 0; i < 3; i++)
if (chip->ac97[i]) if (chip->ac97[i])
snd_ac97_resume(chip->ac97[i]); snd_ac97_resume(chip->ac97[i]);
...@@ -2462,7 +2475,7 @@ static int __devinit snd_intel8x0_create(snd_card_t * card, ...@@ -2462,7 +2475,7 @@ static int __devinit snd_intel8x0_create(snd_card_t * card,
chip->int_sta_reg = device_type == DEVICE_ALI ? ICH_REG_ALI_INTERRUPTSR : ICH_REG_GLOB_STA; chip->int_sta_reg = device_type == DEVICE_ALI ? ICH_REG_ALI_INTERRUPTSR : ICH_REG_GLOB_STA;
chip->int_sta_mask = int_sta_masks; chip->int_sta_mask = int_sta_masks;
if ((err = snd_intel8x0_chip_init(chip)) < 0) { if ((err = snd_intel8x0_chip_init(chip, 1)) < 0) {
snd_intel8x0_free(chip); snd_intel8x0_free(chip);
return err; return err;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment