aboutsummaryrefslogtreecommitdiffstats
path: root/sound
diff options
context:
space:
mode:
Diffstat (limited to 'sound')
-rw-r--r--sound/pci/ens1370.c154
1 files changed, 70 insertions, 84 deletions
diff --git a/sound/pci/ens1370.c b/sound/pci/ens1370.c
index a84f6b21024f..425b167522d5 100644
--- a/sound/pci/ens1370.c
+++ b/sound/pci/ens1370.c
@@ -413,8 +413,6 @@ struct ensoniq {
413 } u; 413 } u;
414 414
415 struct pci_dev *pci; 415 struct pci_dev *pci;
416 unsigned short subsystem_vendor_id;
417 unsigned short subsystem_device_id;
418 struct snd_card *card; 416 struct snd_card *card;
419 struct snd_pcm *pcm1; /* DAC1/ADC PCM */ 417 struct snd_pcm *pcm1; /* DAC1/ADC PCM */
420 struct snd_pcm *pcm2; /* DAC2 PCM */ 418 struct snd_pcm *pcm2; /* DAC2 PCM */
@@ -1607,11 +1605,26 @@ static void snd_ensoniq_mixer_free_ac97(struct snd_ac97 *ac97)
1607 ensoniq->u.es1371.ac97 = NULL; 1605 ensoniq->u.es1371.ac97 = NULL;
1608} 1606}
1609 1607
1610static struct { 1608struct es1371_quirk {
1611 unsigned short vid; /* vendor ID */ 1609 unsigned short vid; /* vendor ID */
1612 unsigned short did; /* device ID */ 1610 unsigned short did; /* device ID */
1613 unsigned char rev; /* revision */ 1611 unsigned char rev; /* revision */
1614} es1371_spdif_present[] __devinitdata = { 1612};
1613
1614static int __devinit es1371_quirk_lookup(struct ensoniq *ensoniq,
1615 struct es1371_quirk *list)
1616{
1617 while (list->vid != (unsigned short)PCI_ANY_ID) {
1618 if (ensoniq->pci->vendor == list->vid &&
1619 ensoniq->pci->device == list->did &&
1620 ensoniq->rev == list->rev)
1621 return 1;
1622 list++;
1623 }
1624 return 0;
1625}
1626
1627static struct es1371_quirk es1371_spdif_present[] __devinitdata = {
1615 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_C }, 1628 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_C },
1616 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_D }, 1629 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_D },
1617 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_E }, 1630 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_E },
@@ -1620,12 +1633,19 @@ static struct {
1620 { .vid = PCI_ANY_ID, .did = PCI_ANY_ID } 1633 { .vid = PCI_ANY_ID, .did = PCI_ANY_ID }
1621}; 1634};
1622 1635
1623static int snd_ensoniq_1371_mixer(struct ensoniq * ensoniq, int has_spdif, int has_line) 1636static struct snd_pci_quirk ens1373_line_quirk[] __devinitdata = {
1637 SND_PCI_QUIRK_ID(0x1274, 0x2000), /* GA-7DXR */
1638 SND_PCI_QUIRK_ID(0x1458, 0xa000), /* GA-8IEXP */
1639 { } /* end */
1640};
1641
1642static int __devinit snd_ensoniq_1371_mixer(struct ensoniq *ensoniq,
1643 int has_spdif, int has_line)
1624{ 1644{
1625 struct snd_card *card = ensoniq->card; 1645 struct snd_card *card = ensoniq->card;
1626 struct snd_ac97_bus *pbus; 1646 struct snd_ac97_bus *pbus;
1627 struct snd_ac97_template ac97; 1647 struct snd_ac97_template ac97;
1628 int err, idx; 1648 int err;
1629 static struct snd_ac97_bus_ops ops = { 1649 static struct snd_ac97_bus_ops ops = {
1630 .write = snd_es1371_codec_write, 1650 .write = snd_es1371_codec_write,
1631 .read = snd_es1371_codec_read, 1651 .read = snd_es1371_codec_read,
@@ -1641,33 +1661,28 @@ static int snd_ensoniq_1371_mixer(struct ensoniq * ensoniq, int has_spdif, int h
1641 ac97.scaps = AC97_SCAP_AUDIO; 1661 ac97.scaps = AC97_SCAP_AUDIO;
1642 if ((err = snd_ac97_mixer(pbus, &ac97, &ensoniq->u.es1371.ac97)) < 0) 1662 if ((err = snd_ac97_mixer(pbus, &ac97, &ensoniq->u.es1371.ac97)) < 0)
1643 return err; 1663 return err;
1644 for (idx = 0; es1371_spdif_present[idx].vid != (unsigned short)PCI_ANY_ID; idx++) 1664 if (has_spdif > 0 ||
1645 if ((ensoniq->pci->vendor == es1371_spdif_present[idx].vid && 1665 (!has_spdif && es1371_quirk_lookup(ensoniq, es1371_spdif_present))) {
1646 ensoniq->pci->device == es1371_spdif_present[idx].did && 1666 struct snd_kcontrol *kctl;
1647 ensoniq->rev == es1371_spdif_present[idx].rev) || has_spdif > 0) { 1667 int i, index = 0;
1648 struct snd_kcontrol *kctl; 1668
1649 int i, index = 0; 1669 ensoniq->spdif_default = ensoniq->spdif_stream =
1650 1670 SNDRV_PCM_DEFAULT_CON_SPDIF;
1651 if (has_spdif < 0) 1671 outl(ensoniq->spdif_default, ES_REG(ensoniq, CHANNEL_STATUS));
1652 break; 1672
1653 1673 if (ensoniq->u.es1371.ac97->ext_id & AC97_EI_SPDIF)
1654 ensoniq->spdif_default = ensoniq->spdif_stream = 1674 index++;
1655 SNDRV_PCM_DEFAULT_CON_SPDIF; 1675
1656 outl(ensoniq->spdif_default, ES_REG(ensoniq, CHANNEL_STATUS)); 1676 for (i = 0; i < ARRAY_SIZE(snd_es1371_mixer_spdif); i++) {
1657 1677 kctl = snd_ctl_new1(&snd_es1371_mixer_spdif[i], ensoniq);
1658 if (ensoniq->u.es1371.ac97->ext_id & AC97_EI_SPDIF) 1678 if (!kctl)
1659 index++; 1679 return -ENOMEM;
1660 1680 kctl->id.index = index;
1661 for (i = 0; i < (int)ARRAY_SIZE(snd_es1371_mixer_spdif); i++) { 1681 err = snd_ctl_add(card, kctl);
1662 kctl = snd_ctl_new1(&snd_es1371_mixer_spdif[i], ensoniq); 1682 if (err < 0)
1663 if (! kctl) 1683 return err;
1664 return -ENOMEM;
1665 kctl->id.index = index;
1666 if ((err = snd_ctl_add(card, kctl)) < 0)
1667 return err;
1668 }
1669 break;
1670 } 1684 }
1685 }
1671 if (ensoniq->u.es1371.ac97->ext_id & AC97_EI_SDAC) { 1686 if (ensoniq->u.es1371.ac97->ext_id & AC97_EI_SDAC) {
1672 /* mirror rear to front speakers */ 1687 /* mirror rear to front speakers */
1673 ensoniq->cssr &= ~(ES_1373_REAR_BIT27|ES_1373_REAR_BIT24); 1688 ensoniq->cssr &= ~(ES_1373_REAR_BIT27|ES_1373_REAR_BIT24);
@@ -1676,12 +1691,10 @@ static int snd_ensoniq_1371_mixer(struct ensoniq * ensoniq, int has_spdif, int h
1676 if (err < 0) 1691 if (err < 0)
1677 return err; 1692 return err;
1678 } 1693 }
1679 if (((ensoniq->subsystem_vendor_id == 0x1274) && 1694 if (has_line > 0 ||
1680 (ensoniq->subsystem_device_id == 0x2000)) || /* GA-7DXR */ 1695 snd_pci_quirk_lookup(ensoniq->pci, ens1373_line_quirk)) {
1681 ((ensoniq->subsystem_vendor_id == 0x1458) && 1696 err = snd_ctl_add(card, snd_ctl_new1(&snd_ens1373_line,
1682 (ensoniq->subsystem_device_id == 0xa000)) || /* GA-8IEXP */ 1697 ensoniq));
1683 has_line > 0) {
1684 err = snd_ctl_add(card, snd_ctl_new1(&snd_ens1373_line, ensoniq));
1685 if (err < 0) 1698 if (err < 0)
1686 return err; 1699 return err;
1687 } 1700 }
@@ -1956,21 +1969,15 @@ static int snd_ensoniq_dev_free(struct snd_device *device)
1956} 1969}
1957 1970
1958#ifdef CHIP1371 1971#ifdef CHIP1371
1959static struct { 1972static struct snd_pci_quirk es1371_amplifier_hack[] __devinitdata = {
1960 unsigned short svid; /* subsystem vendor ID */ 1973 SND_PCI_QUIRK_ID(0x107b, 0x2150), /* Gateway Solo 2150 */
1961 unsigned short sdid; /* subsystem device ID */ 1974 SND_PCI_QUIRK_ID(0x13bd, 0x100c), /* EV1938 on Mebius PC-MJ100V */
1962} es1371_amplifier_hack[] = { 1975 SND_PCI_QUIRK_ID(0x1102, 0x5938), /* Targa Xtender300 */
1963 { .svid = 0x107b, .sdid = 0x2150 }, /* Gateway Solo 2150 */ 1976 SND_PCI_QUIRK_ID(0x1102, 0x8938), /* IPC Topnote G notebook */
1964 { .svid = 0x13bd, .sdid = 0x100c }, /* EV1938 on Mebius PC-MJ100V */ 1977 { } /* end */
1965 { .svid = 0x1102, .sdid = 0x5938 }, /* Targa Xtender300 */
1966 { .svid = 0x1102, .sdid = 0x8938 }, /* IPC Topnote G notebook */
1967 { .svid = PCI_ANY_ID, .sdid = PCI_ANY_ID }
1968}; 1978};
1969static struct { 1979
1970 unsigned short vid; /* vendor ID */ 1980static struct es1371_quirk es1371_ac97_reset_hack[] = {
1971 unsigned short did; /* device ID */
1972 unsigned char rev; /* revision */
1973} es1371_ac97_reset_hack[] = {
1974 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_C }, 1981 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_C },
1975 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_D }, 1982 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_D },
1976 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_E }, 1983 { .vid = PCI_VENDOR_ID_ENSONIQ, .did = PCI_DEVICE_ID_ENSONIQ_CT5880, .rev = CT5880REV_CT5880_E },
@@ -1984,7 +1991,6 @@ static void snd_ensoniq_chip_init(struct ensoniq *ensoniq)
1984{ 1991{
1985#ifdef CHIP1371 1992#ifdef CHIP1371
1986 int idx; 1993 int idx;
1987 struct pci_dev *pci = ensoniq->pci;
1988#endif 1994#endif
1989 /* this code was part of snd_ensoniq_create before intruduction 1995 /* this code was part of snd_ensoniq_create before intruduction
1990 * of suspend/resume 1996 * of suspend/resume
@@ -1999,16 +2005,12 @@ static void snd_ensoniq_chip_init(struct ensoniq *ensoniq)
1999 outl(ensoniq->ctrl, ES_REG(ensoniq, CONTROL)); 2005 outl(ensoniq->ctrl, ES_REG(ensoniq, CONTROL));
2000 outl(ensoniq->sctrl, ES_REG(ensoniq, SERIAL)); 2006 outl(ensoniq->sctrl, ES_REG(ensoniq, SERIAL));
2001 outl(0, ES_REG(ensoniq, 1371_LEGACY)); 2007 outl(0, ES_REG(ensoniq, 1371_LEGACY));
2002 for (idx = 0; es1371_ac97_reset_hack[idx].vid != (unsigned short)PCI_ANY_ID; idx++) 2008 if (es1371_quirk_lookup(ensoniq, es1371_ac97_reset_hack)) {
2003 if (pci->vendor == es1371_ac97_reset_hack[idx].vid && 2009 outl(ensoniq->cssr, ES_REG(ensoniq, STATUS));
2004 pci->device == es1371_ac97_reset_hack[idx].did && 2010 /* need to delay around 20ms(bleech) to give
2005 ensoniq->rev == es1371_ac97_reset_hack[idx].rev) { 2011 some CODECs enough time to wakeup */
2006 outl(ensoniq->cssr, ES_REG(ensoniq, STATUS)); 2012 msleep(20);
2007 /* need to delay around 20ms(bleech) to give 2013 }
2008 some CODECs enough time to wakeup */
2009 msleep(20);
2010 break;
2011 }
2012 /* AC'97 warm reset to start the bitclk */ 2014 /* AC'97 warm reset to start the bitclk */
2013 outl(ensoniq->ctrl | ES_1371_SYNC_RES, ES_REG(ensoniq, CONTROL)); 2015 outl(ensoniq->ctrl | ES_1371_SYNC_RES, ES_REG(ensoniq, CONTROL));
2014 inl(ES_REG(ensoniq, CONTROL)); 2016 inl(ES_REG(ensoniq, CONTROL));
@@ -2112,11 +2114,7 @@ static int __devinit snd_ensoniq_create(struct snd_card *card,
2112 struct ensoniq ** rensoniq) 2114 struct ensoniq ** rensoniq)
2113{ 2115{
2114 struct ensoniq *ensoniq; 2116 struct ensoniq *ensoniq;
2115 unsigned short cmdw;
2116 unsigned char cmdb; 2117 unsigned char cmdb;
2117#ifdef CHIP1371
2118 int idx;
2119#endif
2120 int err; 2118 int err;
2121 static struct snd_device_ops ops = { 2119 static struct snd_device_ops ops = {
2122 .dev_free = snd_ensoniq_dev_free, 2120 .dev_free = snd_ensoniq_dev_free,
@@ -2159,10 +2157,6 @@ static int __devinit snd_ensoniq_create(struct snd_card *card,
2159 pci_set_master(pci); 2157 pci_set_master(pci);
2160 pci_read_config_byte(pci, PCI_REVISION_ID, &cmdb); 2158 pci_read_config_byte(pci, PCI_REVISION_ID, &cmdb);
2161 ensoniq->rev = cmdb; 2159 ensoniq->rev = cmdb;
2162 pci_read_config_word(pci, PCI_SUBSYSTEM_VENDOR_ID, &cmdw);
2163 ensoniq->subsystem_vendor_id = cmdw;
2164 pci_read_config_word(pci, PCI_SUBSYSTEM_ID, &cmdw);
2165 ensoniq->subsystem_device_id = cmdw;
2166#ifdef CHIP1370 2160#ifdef CHIP1370
2167#if 0 2161#if 0
2168 ensoniq->ctrl = ES_1370_CDC_EN | ES_1370_SERR_DISABLE | 2162 ensoniq->ctrl = ES_1370_CDC_EN | ES_1370_SERR_DISABLE |
@@ -2175,19 +2169,11 @@ static int __devinit snd_ensoniq_create(struct snd_card *card,
2175 ensoniq->ctrl = 0; 2169 ensoniq->ctrl = 0;
2176 ensoniq->sctrl = 0; 2170 ensoniq->sctrl = 0;
2177 ensoniq->cssr = 0; 2171 ensoniq->cssr = 0;
2178 for (idx = 0; es1371_amplifier_hack[idx].svid != (unsigned short)PCI_ANY_ID; idx++) 2172 if (snd_pci_quirk_lookup(pci, es1371_amplifier_hack))
2179 if (ensoniq->subsystem_vendor_id == es1371_amplifier_hack[idx].svid && 2173 ensoniq->ctrl |= ES_1371_GPIO_OUT(1); /* turn amplifier on */
2180 ensoniq->subsystem_device_id == es1371_amplifier_hack[idx].sdid) { 2174
2181 ensoniq->ctrl |= ES_1371_GPIO_OUT(1); /* turn amplifier on */ 2175 if (es1371_quirk_lookup(ensoniq, es1371_ac97_reset_hack))
2182 break; 2176 ensoniq->cssr |= ES_1371_ST_AC97_RST;
2183 }
2184 for (idx = 0; es1371_ac97_reset_hack[idx].vid != (unsigned short)PCI_ANY_ID; idx++)
2185 if (pci->vendor == es1371_ac97_reset_hack[idx].vid &&
2186 pci->device == es1371_ac97_reset_hack[idx].did &&
2187 ensoniq->rev == es1371_ac97_reset_hack[idx].rev) {
2188 ensoniq->cssr |= ES_1371_ST_AC97_RST;
2189 break;
2190 }
2191#endif 2177#endif
2192 2178
2193 snd_ensoniq_chip_init(ensoniq); 2179 snd_ensoniq_chip_init(ensoniq);