aboutsummaryrefslogtreecommitdiff
path: root/sound
diff options
context:
space:
mode:
authorJames Morris <jmorris@namei.org>2009-03-24 10:52:46 +1100
committerJames Morris <jmorris@namei.org>2009-03-24 10:52:46 +1100
commit703a3cd72817e99201cef84a8a7aecc60b2b3581 (patch)
tree3e943755178ff410694722bb031f523136fbc432 /sound
parentdf7f54c012b92ec93d56b68547351dcdf8a163d3 (diff)
parent8e0ee43bc2c3e19db56a4adaa9a9b04ce885cd84 (diff)
Merge branch 'master' into next
Diffstat (limited to 'sound')
-rw-r--r--sound/arm/aaci.c6
-rw-r--r--sound/core/jack.c2
-rw-r--r--sound/core/oss/mixer_oss.c3
-rw-r--r--sound/core/oss/pcm_oss.c4
-rw-r--r--sound/core/oss/rate.c2
-rw-r--r--sound/core/sgbuf.c7
-rw-r--r--sound/drivers/mtpav.c3
-rw-r--r--sound/isa/opl3sa2.c18
-rw-r--r--sound/oss/dmasound/dmasound_atari.c16
-rw-r--r--sound/pci/aw2/aw2-alsa.c2
-rw-r--r--sound/pci/emu10k1/emu10k1_main.c1
-rw-r--r--sound/pci/hda/hda_codec.c19
-rw-r--r--sound/pci/hda/hda_codec.h1
-rw-r--r--sound/pci/hda/hda_hwdep.c17
-rw-r--r--sound/pci/hda/hda_intel.c49
-rw-r--r--sound/pci/hda/hda_local.h2
-rw-r--r--sound/pci/hda/patch_analog.c15
-rw-r--r--sound/pci/hda/patch_intelhdmi.c61
-rw-r--r--sound/pci/hda/patch_realtek.c9
-rw-r--r--sound/pci/hda/patch_sigmatel.c21
-rw-r--r--sound/pci/mixart/mixart.c1
-rw-r--r--sound/pci/oxygen/virtuoso.c17
-rw-r--r--sound/pci/pcxhr/pcxhr.h12
-rw-r--r--sound/soc/codecs/tlv320aic3x.c11
-rw-r--r--sound/soc/codecs/wm8990.c4
-rw-r--r--sound/soc/omap/sdp3430.c4
-rw-r--r--sound/soc/soc-core.c5
-rw-r--r--sound/usb/usbaudio.c21
-rw-r--r--sound/usb/usbmidi.c1
29 files changed, 206 insertions, 128 deletions
diff --git a/sound/arm/aaci.c b/sound/arm/aaci.c
index 89096e811a4..772901e41ec 100644
--- a/sound/arm/aaci.c
+++ b/sound/arm/aaci.c
@@ -90,7 +90,7 @@ static void aaci_ac97_write(struct snd_ac97 *ac97, unsigned short reg,
*/
do {
v = readl(aaci->base + AACI_SLFR);
- } while ((v & (SLFR_1TXB|SLFR_2TXB)) && timeout--);
+ } while ((v & (SLFR_1TXB|SLFR_2TXB)) && --timeout);
if (!timeout)
dev_err(&aaci->dev->dev,
@@ -126,7 +126,7 @@ static unsigned short aaci_ac97_read(struct snd_ac97 *ac97, unsigned short reg)
*/
do {
v = readl(aaci->base + AACI_SLFR);
- } while ((v & SLFR_1TXB) && timeout--);
+ } while ((v & SLFR_1TXB) && --timeout);
if (!timeout) {
dev_err(&aaci->dev->dev, "timeout on slot 1 TX busy\n");
@@ -147,7 +147,7 @@ static unsigned short aaci_ac97_read(struct snd_ac97 *ac97, unsigned short reg)
do {
cond_resched();
v = readl(aaci->base + AACI_SLFR) & (SLFR_1RXV|SLFR_2RXV);
- } while ((v != (SLFR_1RXV|SLFR_2RXV)) && timeout--);
+ } while ((v != (SLFR_1RXV|SLFR_2RXV)) && --timeout);
if (!timeout) {
dev_err(&aaci->dev->dev, "timeout on RX valid\n");
diff --git a/sound/core/jack.c b/sound/core/jack.c
index dd4a12dc09a..077a85262c1 100644
--- a/sound/core/jack.c
+++ b/sound/core/jack.c
@@ -47,7 +47,7 @@ static int snd_jack_dev_register(struct snd_device *device)
int err;
snprintf(jack->name, sizeof(jack->name), "%s %s",
- card->longname, jack->id);
+ card->shortname, jack->id);
jack->input_dev->name = jack->name;
/* Default to the sound card device. */
diff --git a/sound/core/oss/mixer_oss.c b/sound/core/oss/mixer_oss.c
index 4690b8b5681..e570649184e 100644
--- a/sound/core/oss/mixer_oss.c
+++ b/sound/core/oss/mixer_oss.c
@@ -692,6 +692,9 @@ static int snd_mixer_oss_put_volume1(struct snd_mixer_oss_file *fmixer,
snd_mixer_oss_put_volume1_vol(fmixer, pslot, slot->numid[SNDRV_MIXER_OSS_ITEM_PVOLUME], left, right);
if (slot->present & SNDRV_MIXER_OSS_PRESENT_CVOLUME)
snd_mixer_oss_put_volume1_vol(fmixer, pslot, slot->numid[SNDRV_MIXER_OSS_ITEM_CVOLUME], left, right);
+ } else if (slot->present & SNDRV_MIXER_OSS_PRESENT_CVOLUME) {
+ snd_mixer_oss_put_volume1_vol(fmixer, pslot,
+ slot->numid[SNDRV_MIXER_OSS_ITEM_CVOLUME], left, right);
} else if (slot->present & SNDRV_MIXER_OSS_PRESENT_GVOLUME) {
snd_mixer_oss_put_volume1_vol(fmixer, pslot, slot->numid[SNDRV_MIXER_OSS_ITEM_GVOLUME], left, right);
} else if (slot->present & SNDRV_MIXER_OSS_PRESENT_GLOBAL) {
diff --git a/sound/core/oss/pcm_oss.c b/sound/core/oss/pcm_oss.c
index 0a1798eafb0..699d2890535 100644
--- a/sound/core/oss/pcm_oss.c
+++ b/sound/core/oss/pcm_oss.c
@@ -2872,7 +2872,7 @@ static void snd_pcm_oss_proc_write(struct snd_info_entry *entry,
setup = kmalloc(sizeof(*setup), GFP_KERNEL);
if (! setup) {
buffer->error = -ENOMEM;
- mutex_lock(&pstr->oss.setup_mutex);
+ mutex_unlock(&pstr->oss.setup_mutex);
return;
}
if (pstr->oss.setup_list == NULL)
@@ -2886,7 +2886,7 @@ static void snd_pcm_oss_proc_write(struct snd_info_entry *entry,
if (! template.task_name) {
kfree(setup);
buffer->error = -ENOMEM;
- mutex_lock(&pstr->oss.setup_mutex);
+ mutex_unlock(&pstr->oss.setup_mutex);
return;
}
}
diff --git a/sound/core/oss/rate.c b/sound/core/oss/rate.c
index a466443c4a2..2fa9299a440 100644
--- a/sound/core/oss/rate.c
+++ b/sound/core/oss/rate.c
@@ -157,7 +157,7 @@ static void resample_shrink(struct snd_pcm_plugin *plugin,
while (dst_frames1 > 0) {
S1 = S2;
if (src_frames1-- > 0) {
- S1 = *src;
+ S2 = *src;
src += src_step;
}
if (pos & ~R_MASK) {
diff --git a/sound/core/sgbuf.c b/sound/core/sgbuf.c
index d4564edd61d..4e7ec2b4987 100644
--- a/sound/core/sgbuf.c
+++ b/sound/core/sgbuf.c
@@ -38,6 +38,10 @@ int snd_free_sgbuf_pages(struct snd_dma_buffer *dmab)
if (! sgbuf)
return -EINVAL;
+ if (dmab->area)
+ vunmap(dmab->area);
+ dmab->area = NULL;
+
tmpb.dev.type = SNDRV_DMA_TYPE_DEV;
tmpb.dev.dev = sgbuf->dev;
for (i = 0; i < sgbuf->pages; i++) {
@@ -48,9 +52,6 @@ int snd_free_sgbuf_pages(struct snd_dma_buffer *dmab)
tmpb.bytes = (sgbuf->table[i].addr & ~PAGE_MASK) << PAGE_SHIFT;
snd_dma_free_pages(&tmpb);
}
- if (dmab->area)
- vunmap(dmab->area);
- dmab->area = NULL;
kfree(sgbuf->table);
kfree(sgbuf->page_table);
diff --git a/sound/drivers/mtpav.c b/sound/drivers/mtpav.c
index 5b89c0883d6..48b64e6b267 100644
--- a/sound/drivers/mtpav.c
+++ b/sound/drivers/mtpav.c
@@ -706,7 +706,6 @@ static int __devinit snd_mtpav_probe(struct platform_device *dev)
mtp_card->card = card;
mtp_card->irq = -1;
mtp_card->share_irq = 0;
- mtp_card->inmidiport = 0xffffffff;
mtp_card->inmidistate = 0;
mtp_card->outmidihwport = 0xffffffff;
init_timer(&mtp_card->timer);
@@ -719,6 +718,8 @@ static int __devinit snd_mtpav_probe(struct platform_device *dev)
if (err < 0)
goto __error;
+ mtp_card->inmidiport = mtp_card->num_ports + MTPAV_PIDX_BROADCAST;
+
err = snd_mtpav_get_ISA(mtp_card);
if (err < 0)
goto __error;
diff --git a/sound/isa/opl3sa2.c b/sound/isa/opl3sa2.c
index 58c972b2af0..b848d100186 100644
--- a/sound/isa/opl3sa2.c
+++ b/sound/isa/opl3sa2.c
@@ -550,21 +550,27 @@ static int __devinit snd_opl3sa2_mixer(struct snd_card *card)
#ifdef CONFIG_PM
static int snd_opl3sa2_suspend(struct snd_card *card, pm_message_t state)
{
- struct snd_opl3sa2 *chip = card->private_data;
+ if (card) {
+ struct snd_opl3sa2 *chip = card->private_data;
- snd_power_change_state(card, SNDRV_CTL_POWER_D3hot);
- chip->wss->suspend(chip->wss);
- /* power down */
- snd_opl3sa2_write(chip, OPL3SA2_PM_CTRL, OPL3SA2_PM_D3);
+ snd_power_change_state(card, SNDRV_CTL_POWER_D3hot);
+ chip->wss->suspend(chip->wss);
+ /* power down */
+ snd_opl3sa2_write(chip, OPL3SA2_PM_CTRL, OPL3SA2_PM_D3);
+ }
return 0;
}
static int snd_opl3sa2_resume(struct snd_card *card)
{
- struct snd_opl3sa2 *chip = card->private_data;
+ struct snd_opl3sa2 *chip;
int i;
+ if (!card)
+ return 0;
+
+ chip = card->private_data;
/* power up */
snd_opl3sa2_write(chip, OPL3SA2_PM_CTRL, OPL3SA2_PM_D0);
diff --git a/sound/oss/dmasound/dmasound_atari.c b/sound/oss/dmasound/dmasound_atari.c
index 57d9f154c88..38931f2f696 100644
--- a/sound/oss/dmasound/dmasound_atari.c
+++ b/sound/oss/dmasound/dmasound_atari.c
@@ -847,23 +847,23 @@ static int __init AtaIrqInit(void)
of events. So all we need to keep the music playing is
to provide the sound hardware with new data upon
an interrupt from timer A. */
- mfp.tim_ct_a = 0; /* ++roman: Stop timer before programming! */
- mfp.tim_dt_a = 1; /* Cause interrupt after first event. */
- mfp.tim_ct_a = 8; /* Turn on event counting. */
+ st_mfp.tim_ct_a = 0; /* ++roman: Stop timer before programming! */
+ st_mfp.tim_dt_a = 1; /* Cause interrupt after first event. */
+ st_mfp.tim_ct_a = 8; /* Turn on event counting. */
/* Register interrupt handler. */
if (request_irq(IRQ_MFP_TIMA, AtaInterrupt, IRQ_TYPE_SLOW, "DMA sound",
AtaInterrupt))
return 0;
- mfp.int_en_a |= 0x20; /* Turn interrupt on. */
- mfp.int_mk_a |= 0x20;
+ st_mfp.int_en_a |= 0x20; /* Turn interrupt on. */
+ st_mfp.int_mk_a |= 0x20;
return 1;
}
#ifdef MODULE
static void AtaIrqCleanUp(void)
{
- mfp.tim_ct_a = 0; /* stop timer */
- mfp.int_en_a &= ~0x20; /* turn interrupt off */
+ st_mfp.tim_ct_a = 0; /* stop timer */
+ st_mfp.int_en_a &= ~0x20; /* turn interrupt off */
free_irq(IRQ_MFP_TIMA, AtaInterrupt);
}
#endif /* MODULE */
@@ -1599,7 +1599,7 @@ static int __init dmasound_atari_init(void)
is_falcon = 0;
} else
return -ENODEV;
- if ((mfp.int_en_a & mfp.int_mk_a & 0x20) == 0)
+ if ((st_mfp.int_en_a & st_mfp.int_mk_a & 0x20) == 0)
return dmasound_init();
else {
printk("DMA sound driver: Timer A interrupt already in use\n");
diff --git a/sound/pci/aw2/aw2-alsa.c b/sound/pci/aw2/aw2-alsa.c
index 3f00ddf450f..c7c54e7748e 100644
--- a/sound/pci/aw2/aw2-alsa.c
+++ b/sound/pci/aw2/aw2-alsa.c
@@ -165,7 +165,7 @@ module_param_array(enable, bool, NULL, 0444);
MODULE_PARM_DESC(enable, "Enable Audiowerk2 soundcard.");
static struct pci_device_id snd_aw2_ids[] = {
- {PCI_VENDOR_ID_SAA7146, PCI_DEVICE_ID_SAA7146, PCI_ANY_ID, PCI_ANY_ID,
+ {PCI_VENDOR_ID_SAA7146, PCI_DEVICE_ID_SAA7146, 0, 0,
0, 0, 0},
{0}
};
diff --git a/sound/pci/emu10k1/emu10k1_main.c b/sound/pci/emu10k1/emu10k1_main.c
index 7958006a1d6..101a1c13a20 100644
--- a/sound/pci/emu10k1/emu10k1_main.c
+++ b/sound/pci/emu10k1/emu10k1_main.c
@@ -1528,6 +1528,7 @@ static struct snd_emu_chip_details emu_chip_details[] = {
.ca0151_chip = 1,
.spk71 = 1,
.spdif_bug = 1,
+ .invert_shared_spdif = 1, /* digital/analog switch swapped */
.ac97_chip = 1} ,
{.vendor = 0x1102, .device = 0x0004, .subsystem = 0x10021102,
.driver = "Audigy2", .name = "SB Audigy 2 Platinum [SB0240P]",
diff --git a/sound/pci/hda/hda_codec.c b/sound/pci/hda/hda_codec.c
index b7bba7dc7cf..d03f99298be 100644
--- a/sound/pci/hda/hda_codec.c
+++ b/sound/pci/hda/hda_codec.c
@@ -487,7 +487,6 @@ int /*__devinit*/ snd_hda_bus_new(struct snd_card *card,
{
struct hda_bus *bus;
int err;
- char qname[8];
static struct snd_device_ops dev_ops = {
.dev_register = snd_hda_bus_dev_register,
.dev_free = snd_hda_bus_dev_free,
@@ -517,10 +516,12 @@ int /*__devinit*/ snd_hda_bus_new(struct snd_card *card,
mutex_init(&bus->cmd_mutex);
INIT_LIST_HEAD(&bus->codec_list);
- snprintf(qname, sizeof(qname), "hda%d", card->number);
- bus->workq = create_workqueue(qname);
+ snprintf(bus->workq_name, sizeof(bus->workq_name),
+ "hd-audio%d", card->number);
+ bus->workq = create_singlethread_workqueue(bus->workq_name);
if (!bus->workq) {
- snd_printk(KERN_ERR "cannot create workqueue %s\n", qname);
+ snd_printk(KERN_ERR "cannot create workqueue %s\n",
+ bus->workq_name);
kfree(bus);
return -ENOMEM;
}
@@ -3087,6 +3088,16 @@ int snd_hda_multi_out_dig_prepare(struct hda_codec *codec,
}
EXPORT_SYMBOL_HDA(snd_hda_multi_out_dig_prepare);
+int snd_hda_multi_out_dig_cleanup(struct hda_codec *codec,
+ struct hda_multi_out *mout)
+{
+ mutex_lock(&codec->spdif_mutex);
+ cleanup_dig_out_stream(codec, mout->dig_out_nid);
+ mutex_unlock(&codec->spdif_mutex);
+ return 0;
+}
+EXPORT_SYMBOL_HDA(snd_hda_multi_out_dig_cleanup);
+
/*
* release the digital out
*/
diff --git a/sound/pci/hda/hda_codec.h b/sound/pci/hda/hda_codec.h
index 5810ef58840..09a332ada0c 100644
--- a/sound/pci/hda/hda_codec.h
+++ b/sound/pci/hda/hda_codec.h
@@ -614,6 +614,7 @@ struct hda_bus {
/* unsolicited event queue */
struct hda_bus_unsolicited *unsol;
+ char workq_name[16];
struct workqueue_struct *workq; /* common workqueue for codecs */
/* assigned PCMs */
diff --git a/sound/pci/hda/hda_hwdep.c b/sound/pci/hda/hda_hwdep.c
index 300ab407cf4..4ae51dcb81a 100644
--- a/sound/pci/hda/hda_hwdep.c
+++ b/sound/pci/hda/hda_hwdep.c
@@ -175,7 +175,7 @@ static int reconfig_codec(struct hda_codec *codec)
err = snd_hda_codec_build_controls(codec);
if (err < 0)
return err;
- return 0;
+ return snd_card_register(codec->bus->card);
}
/*
@@ -277,18 +277,19 @@ static ssize_t init_verbs_store(struct device *dev,
{
struct snd_hwdep *hwdep = dev_get_drvdata(dev);
struct hda_codec *codec = hwdep->private_data;
- char *p;
- struct hda_verb verb, *v;
+ struct hda_verb *v;
+ int nid, verb, param;
- verb.nid = simple_strtoul(buf, &p, 0);
- verb.verb = simple_strtoul(p, &p, 0);
- verb.param = simple_strtoul(p, &p, 0);
- if (!verb.nid || !verb.verb || !verb.param)
+ if (sscanf(buf, "%i %i %i", &nid, &verb, &param) != 3)
+ return -EINVAL;
+ if (!nid || !verb)
return -EINVAL;
v = snd_array_new(&codec->init_verbs);
if (!v)
return -ENOMEM;
- *v = verb;
+ v->nid = nid;
+ v->verb = verb;
+ v->param = param;
return count;
}
diff --git a/sound/pci/hda/hda_intel.c b/sound/pci/hda/hda_intel.c
index 11e791b965f..f3b5723c285 100644
--- a/sound/pci/hda/hda_intel.c
+++ b/sound/pci/hda/hda_intel.c
@@ -1947,16 +1947,13 @@ static int azx_suspend(struct pci_dev *pci, pm_message_t state)
return 0;
}
-static int azx_resume_early(struct pci_dev *pci)
-{
- return pci_restore_state(pci);
-}
-
static int azx_resume(struct pci_dev *pci)
{
struct snd_card *card = pci_get_drvdata(pci);
struct azx *chip = card->private_data;
+ pci_set_power_state(pci, PCI_D0);
+ pci_restore_state(pci);
if (pci_enable_device(pci) < 0) {
printk(KERN_ERR "hda-intel: pci_enable_device failed, "
"disabling device\n");
@@ -2062,26 +2059,31 @@ static int __devinit check_position_fix(struct azx *chip, int fix)
{
const struct snd_pci_quirk *q;
- /* Check VIA HD Audio Controller exist */
- if (chip->pci->vendor == PCI_VENDOR_ID_VIA &&
- chip->pci->device == VIA_HDAC_DEVICE_ID) {
+ switch (fix) {
+ case POS_FIX_LPIB:
+ case POS_FIX_POSBUF:
+ return fix;
+ }
+
+ /* Check VIA/ATI HD Audio Controller exist */
+ switch (chip->driver_type) {
+ case AZX_DRIVER_VIA:
+ case AZX_DRIVER_ATI:
chip->via_dmapos_patch = 1;
/* Use link position directly, avoid any transfer problem. */
return POS_FIX_LPIB;
}
chip->via_dmapos_patch = 0;
- if (fix == POS_FIX_AUTO) {
- q = snd_pci_quirk_lookup(chip->pci, position_fix_list);
- if (q) {
- printk(KERN_INFO
- "hda_intel: position_fix set to %d "
- "for device %04x:%04x\n",
- q->value, q->subvendor, q->subdevice);
- return q->value;
- }
+ q = snd_pci_quirk_lookup(chip->pci, position_fix_list);
+ if (q) {
+ printk(KERN_INFO
+ "hda_intel: position_fix set to %d "
+ "for device %04x:%04x\n",
+ q->value, q->subvendor, q->subdevice);
+ return q->value;
}
- return fix;
+ return POS_FIX_AUTO;
}
/*
@@ -2098,6 +2100,8 @@ static struct snd_pci_quirk probe_mask_list[] __devinitdata = {
SND_PCI_QUIRK(0x1028, 0x20ac, "Dell Studio Desktop", 0x01),
/* including bogus ALC268 in slot#2 that conflicts with ALC888 */
SND_PCI_QUIRK(0x17c0, 0x4085, "Medion MD96630", 0x01),
+ /* conflict of ALC268 in slot#3 (digital I/O); a temporary fix */
+ SND_PCI_QUIRK(0x1179, 0xff00, "Toshiba laptop", 0x03),
{}
};
@@ -2211,9 +2215,17 @@ static int __devinit azx_create(struct snd_card *card, struct pci_dev *pci,
gcap = azx_readw(chip, GCAP);
snd_printdd("chipset global capabilities = 0x%x\n", gcap);
+ /* ATI chips seems buggy about 64bit DMA addresses */
+ if (chip->driver_type == AZX_DRIVER_ATI)
+ gcap &= ~0x01;
+
/* allow 64bit DMA address if supported by H/W */
if ((gcap & 0x01) && !pci_set_dma_mask(pci, DMA_64BIT_MASK))
pci_set_consistent_dma_mask(pci, DMA_64BIT_MASK);
+ else {
+ pci_set_dma_mask(pci, DMA_32BIT_MASK);
+ pci_set_consistent_dma_mask(pci, DMA_32BIT_MASK);
+ }
/* read number of streams from GCAP register instead of using
* hardcoded value
@@ -2468,7 +2480,6 @@ static struct pci_driver driver = {
.remove = __devexit_p(azx_remove),
#ifdef CONFIG_PM
.suspend = azx_suspend,
- .resume_early = azx_resume_early,
.resume = azx_resume,
#endif
};
diff --git a/sound/pci/hda/hda_local.h b/sound/pci/hda/hda_local.h
index 1dd8716c387..44f189cb97a 100644
--- a/sound/pci/hda/hda_local.h
+++ b/sound/pci/hda/hda_local.h
@@ -251,6 +251,8 @@ int snd_hda_multi_out_dig_prepare(struct hda_codec *codec,
unsigned int stream_tag,
unsigned int format,
struct snd_pcm_substream *substream);
+int snd_hda_multi_out_dig_cleanup(struct hda_codec *codec,
+ struct hda_multi_out *mout);
int snd_hda_multi_out_analog_open(struct hda_codec *codec,
struct hda_multi_out *mout,
struct snd_pcm_substream *substream,
diff --git a/sound/pci/hda/patch_analog.c b/sound/pci/hda/patch_analog.c
index 2e7371ec2e2..e48612323aa 100644
--- a/sound/pci/hda/patch_analog.c
+++ b/sound/pci/hda/patch_analog.c
@@ -275,6 +275,14 @@ static int ad198x_dig_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
format, substream);
}
+static int ad198x_dig_playback_pcm_cleanup(struct hda_pcm_stream *hinfo,
+ struct hda_codec *codec,
+ struct snd_pcm_substream *substream)
+{
+ struct ad198x_spec *spec = codec->spec;
+ return snd_hda_multi_out_dig_cleanup(codec, &spec->multiout);
+}
+
/*
* Analog capture
*/
@@ -333,7 +341,8 @@ static struct hda_pcm_stream ad198x_pcm_digital_playback = {
.ops = {
.open = ad198x_dig_playback_pcm_open,
.close = ad198x_dig_playback_pcm_close,
- .prepare = ad198x_dig_playback_pcm_prepare
+ .prepare = ad198x_dig_playback_pcm_prepare,
+ .cleanup = ad198x_dig_playback_pcm_cleanup
},
};
@@ -1885,8 +1894,8 @@ static hda_nid_t ad1988_capsrc_nids[3] = {
#define AD1988_SPDIF_OUT_HDMI 0x0b
#define AD1988_SPDIF_IN 0x07
-static hda_nid_t ad1989b_slave_dig_outs[2] = {
- AD1988_SPDIF_OUT, AD1988_SPDIF_OUT_HDMI
+static hda_nid_t ad1989b_slave_dig_outs[] = {
+ AD1988_SPDIF_OUT, AD1988_SPDIF_OUT_HDMI, 0
};
static struct hda_input_mux ad1988_6stack_capture_source = {
diff --git a/sound/pci/hda/patch_intelhdmi.c b/sound/pci/hda/patch_intelhdmi.c
index 3564f4e4b74..fcc77fec448 100644
--- a/sound/pci/hda/patch_intelhdmi.c
+++ b/sound/pci/hda/patch_intelhdmi.c
@@ -49,11 +49,6 @@ static struct hda_verb pinout_enable_verb[] = {
{} /* terminator */
};
-static struct hda_verb pinout_disable_verb[] = {
- {PIN_NID, AC_VERB_SET_PIN_WIDGET_CONTROL, 0x00},
- {}
-};
-
static struct hda_verb unsolicited_response_verb[] = {
{PIN_NID, AC_VERB_SET_UNSOLICITED_ENABLE, AC_USRSP_EN |
INTEL_HDMI_EVENT_TAG},
@@ -248,10 +243,6 @@ static void hdmi_write_dip_byte(struct hda_codec *codec, hda_nid_t nid,
static void hdmi_enable_output(struct hda_codec *codec)
{
- /* Enable Audio InfoFrame Transmission */
- hdmi_set_dip_index(codec, PIN_NID, 0x0, 0x0);
- snd_hda_codec_write(codec, PIN_NID, 0, AC_VERB_SET_HDMI_DIP_XMIT,
- AC_DIPXMIT_BEST);
/* Unmute */
if (get_wcaps(codec, PIN_NID) & AC_WCAP_OUT_AMP)
snd_hda_codec_write(codec, PIN_NID, 0,
@@ -260,17 +251,24 @@ static void hdmi_enable_output(struct hda_codec *codec)
snd_hda_sequence_write(codec, pinout_enable_verb);
}
-static void hdmi_disable_output(struct hda_codec *codec)
+/*
+ * Enable Audio InfoFrame Transmission
+ */
+static void hdmi_start_infoframe_trans(struct hda_codec *codec)
{
- snd_hda_sequence_write(codec, pinout_disable_verb);
- if (get_wcaps(codec, PIN_NID) & AC_WCAP_OUT_AMP)
- snd_hda_codec_write(codec, PIN_NID, 0,
- AC_VERB_SET_AMP_GAIN_MUTE, AMP_OUT_MUTE);
+ hdmi_set_dip_index(codec, PIN_NID, 0x0, 0x0);
+ snd_hda_codec_write(codec, PIN_NID, 0, AC_VERB_SET_HDMI_DIP_XMIT,
+ AC_DIPXMIT_BEST);
+}
- /*
- * FIXME: noises may arise when playing music after reloading the
- * kernel module, until the next X restart or monitor repower.
- */
+/*
+ * Disable Audio InfoFrame Transmission
+ */
+static void hdmi_stop_infoframe_trans(struct hda_codec *codec)
+{
+ hdmi_set_dip_index(codec, PIN_NID, 0x0, 0x0);
+ snd_hda_codec_write(codec, PIN_NID, 0, AC_VERB_SET_HDMI_DIP_XMIT,
+ AC_DIPXMIT_DISABLE);
}
static int hdmi_get_channel_count(struct hda_codec *codec)
@@ -368,11 +366,16 @@ static void hdmi_fill_audio_infoframe(struct hda_codec *codec,
struct hdmi_audio_infoframe *ai)
{
u8 *params = (u8 *)ai;
+ u8 sum = 0;
int i;
hdmi_debug_dip_size(codec);
hdmi_clear_dip_buffers(codec); /* be paranoid */
+ for (i = 0; i < sizeof(ai); i++)
+ sum += params[i];
+ ai->checksum = - sum;
+
hdmi_set_dip_index(codec, PIN_NID, 0x0, 0x0);
for (i = 0; i < sizeof(ai); i++)
hdmi_write_dip_byte(codec, PIN_NID, params[i]);
@@ -419,14 +422,18 @@ static int hdmi_setup_channel_allocation(struct hda_codec *codec,
/*
* CA defaults to 0 for basic stereo audio
*/
- if (!eld->eld_ver)
- return 0;
- if (!eld->spk_alloc)
- return 0;
if (channels <= 2)
return 0;
/*
+ * HDMI sink's ELD info cannot always be retrieved for now, e.g.
+ * in console or for audio devices. Assume the highest speakers
+ * configuration, to _not_ prohibit multi-channel audio playback.
+ */
+ if (!eld->spk_alloc)
+ eld->spk_alloc = 0xffff;
+
+ /*
* expand ELD's speaker allocation mask
*
* ELD tells the speaker mask in a compact(paired) form,
@@ -485,6 +492,7 @@ static void hdmi_setup_audio_infoframe(struct hda_codec *codec,
hdmi_setup_channel_mapping(codec, &ai);
hdmi_fill_audio_infoframe(codec, &ai);
+ hdmi_start_infoframe_trans(codec);
}
@@ -562,7 +570,7 @@ static int intel_hdmi_playback_pcm_close(struct hda_pcm_stream *hinfo,
{
struct intel_hdmi_spec *spec = codec->spec;
- hdmi_disable_output(codec);
+ hdmi_stop_infoframe_trans(codec);
return snd_hda_multi_out_dig_close(codec, &spec->multiout);
}
@@ -582,8 +590,6 @@ static int intel_hdmi_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
hdmi_setup_audio_infoframe(codec, substream);
- hdmi_enable_output(codec);
-
return 0;
}
@@ -628,8 +634,7 @@ static int intel_hdmi_build_controls(struct hda_codec *codec)
static int intel_hdmi_init(struct hda_codec *codec)
{
- /* disable audio output as early as possible */
- hdmi_disable_output(codec);
+ hdmi_enable_output(codec);
snd_hda_sequence_write(codec, unsolicited_response_verb);
@@ -679,6 +684,7 @@ static struct hda_codec_preset snd_hda_preset_intelhdmi[] = {
{ .id = 0x80862801, .name = "G45 DEVBLC", .patch = patch_intel_hdmi },
{ .id = 0x80862802, .name = "G45 DEVCTG", .patch = patch_intel_hdmi },
{ .id = 0x80862803, .name = "G45 DEVELK", .patch = patch_intel_hdmi },
+ { .id = 0x80862804, .name = "G45 DEVIBX", .patch = patch_intel_hdmi },
{ .id = 0x10951392, .name = "SiI1392 HDMI", .patch = patch_intel_hdmi },
{} /* terminator */
};
@@ -687,6 +693,7 @@ MODULE_ALIAS("snd-hda-codec-id:808629fb");
MODULE_ALIAS("snd-hda-codec-id:80862801");
MODULE_ALIAS("snd-hda-codec-id:80862802");
MODULE_ALIAS("snd-hda-codec-id:80862803");
+MODULE_ALIAS("snd-hda-codec-id:80862804");
MODULE_ALIAS("snd-hda-codec-id:10951392");
MODULE_LICENSE("GPL");
diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c
index 0040101f615..6c26afcb826 100644
--- a/sound/pci/hda/patch_realtek.c
+++ b/sound/pci/hda/patch_realtek.c
@@ -1037,6 +1037,7 @@ do_sku:
case 0x10ec0267:
case 0x10ec0268:
case 0x10ec0269:
+ case 0x10ec0272:
case 0x10ec0660:
case 0x10ec0662:
case 0x10ec0663:
@@ -1065,6 +1066,7 @@ do_sku:
case 0x10ec0882:
case 0x10ec0883:
case 0x10ec0885:
+ case 0x10ec0887:
case 0x10ec0889:
snd_hda_codec_write(codec, 0x20, 0,
AC_VERB_SET_COEF_INDEX, 7);
@@ -7015,6 +7017,7 @@ static int patch_alc882(struct hda_codec *codec)
case 0x106b3e00: /* iMac 24 Aluminium */
board_config = ALC885_IMAC24;
break;
+ case 0x106b00a0: /* MacBookPro3,1 - Another revision */
case 0x106b00a1: /* Macbook (might be wrong - PCI SSID?) */
case 0x106b00a4: /* MacbookPro4,1 */
case 0x106b2c00: /* Macbook Pro rev3 */
@@ -8467,6 +8470,8 @@ static struct snd_pci_quirk alc883_cfg_tbl[] = {
ALC888_ACER_ASPIRE_4930G),
SND_PCI_QUIRK(0x1025, 0x015e, "Acer Aspire 6930G",
ALC888_ACER_ASPIRE_4930G),
+ SND_PCI_QUIRK(0x1025, 0x0166, "Acer Aspire 6530G",
+ ALC888_ACER_ASPIRE_4930G),
SND_PCI_QUIRK(0x1025, 0, "Acer laptop", ALC883_ACER), /* default Acer */
SND_PCI_QUIRK(0x1028, 0x020d, "Dell Inspiron 530", ALC888_6ST_DELL),
SND_PCI_QUIRK(0x103c, 0x2a3d, "HP Pavillion", ALC883_6ST_DIG),
@@ -8476,6 +8481,7 @@ static struct snd_pci_quirk alc883_cfg_tbl[] = {
SND_PCI_QUIRK(0x103c, 0x2a66, "HP Acacia", ALC888_3ST_HP),
SND_PCI_QUIRK(0x1043, 0x1873, "Asus M90V", ALC888_ASUS_M90V),
SND_PCI_QUIRK(0x1043, 0x8249, "Asus M2A-VM HDMI", ALC883_3ST_6ch_DIG),
+ SND_PCI_QUIRK(0x1043, 0x8284, "Asus Z37E", ALC883_6ST_DIG),
SND_PCI_QUIRK(0x1043, 0x82fe, "Asus P5Q-EM HDMI", ALC1200_ASUS_P5Q),
SND_PCI_QUIRK(0x1043, 0x835f, "Asus Eee 1601", ALC888_ASUS_EEE1601),
SND_PCI_QUIRK(0x105b, 0x0ce8, "Foxconn P35AX-S", ALC883_6ST_DIG),
@@ -8515,6 +8521,8 @@ static struct snd_pci_quirk alc883_cfg_tbl[] = {
SND_PCI_QUIRK(0x1558, 0, "Clevo laptop", ALC883_LAPTOP_EAPD),
SND_PCI_QUIRK(0x15d9, 0x8780, "Supermicro PDSBA", ALC883_3ST_6ch),
SND_PCI_QUIRK(0x161f, 0x2054, "Medion laptop", ALC883_MEDION),
+ SND_PCI_QUIRK(0x1734, 0x1107, "FSC AMILO Xi2550",
+ ALC883_FUJITSU_PI2515),
SND_PCI_QUIRK(0x1734, 0x1108, "Fujitsu AMILO Pi2515", ALC883_FUJITSU_PI2515),
SND_PCI_QUIRK(0x1734, 0x113d, "Fujitsu AMILO Xa3530",
ALC888_FUJITSU_XA3530),
@@ -10549,6 +10557,7 @@ static struct snd_pci_quirk alc262_cfg_tbl[] = {
SND_PCI_QUIRK(0x103c, 0x1309, "HP xw4*00", ALC262_HP_BPC),
SND_PCI_QUIRK(0x103c, 0x130a, "HP xw6*00", ALC262_HP_BPC),
SND_PCI_QUIRK(0x103c, 0x130b, "HP xw8*00", ALC262_HP_BPC),
+ SND_PCI_QUIRK(0x103c, 0x170b, "HP xw*", ALC262_HP_BPC),
SND_PCI_QUIRK(0x103c, 0x2800, "HP D7000", ALC262_HP_BPC_D7000_WL),
SND_PCI_QUIRK(0x103c, 0x2801, "HP D7000", ALC262_HP_BPC_D7000_WF),
SND_PCI_QUIRK(0x103c, 0x2802, "HP D7000", ALC262_HP_BPC_D7000_WL),
diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c
index 38428e22428..6094344fb22 100644
--- a/sound/pci/hda/patch_sigmatel.c
+++ b/sound/pci/hda/patch_sigmatel.c
@@ -1207,7 +1207,7 @@ static const char *slave_vols[] = {
"LFE Playback Volume",
"Side Playback Volume",
"Headphone Playback Volume",
- "Headphone Playback Volume",
+ "Headphone2 Playback Volume",
"Speaker Playback Volume",
"External Speaker Playback Volume",
"Speaker2 Playback Volume",
@@ -1221,7 +1221,7 @@ static const char *slave_sws[] = {
"LFE Playback Switch",
"Side Playback Switch",
"Headphone Playback Switch",
- "Headphone Playback Switch",
+ "Headphone2 Playback Switch",
"Speaker Playback Switch",
"External Speaker Playback Switch",
"Speaker2 Playback Switch",
@@ -1799,7 +1799,7 @@ static struct snd_pci_quirk stac92hd71bxx_cfg_tbl[] = {
SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x30f2,
"HP dv5", STAC_HP_M4),
SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x30f4,
- "HP dv7", STAC_HP_M4),
+ "HP dv7", STAC_HP_DV5),
SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x30f7,
"HP dv4", STAC_HP_DV5),
SND_PCI_QUIRK(PCI_VENDOR_ID_HP, 0x30fc,
@@ -2442,6 +2442,14 @@ static int stac92xx_dig_playback_pcm_prepare(struct hda_pcm_stream *hinfo,
stream_tag, format, substream);
}
+static int stac92xx_dig_playback_pcm_cleanup(struct hda_pcm_stream *hinfo,
+ struct hda_codec *codec,
+ struct snd_pcm_substream *substream)
+{
+ struct sigmatel_spec *spec = codec->spec;
+ return snd_hda_multi_out_dig_cleanup(codec, &spec->multiout);
+}
+
/*
* Analog capture callbacks
@@ -2486,7 +2494,8 @@ static struct hda_pcm_stream stac92xx_pcm_digital_playback = {
.ops = {
.open = stac92xx_dig_playback_pcm_open,
.close = stac92xx_dig_playback_pcm_close,
- .prepare = stac92xx_dig_playback_pcm_prepare
+ .prepare = stac92xx_dig_playback_pcm_prepare,
+ .cleanup = stac92xx_dig_playback_pcm_cleanup
},
};
@@ -3507,6 +3516,7 @@ static int stac92xx_parse_auto_config(struct hda_codec *codec, hda_nid_t dig_out
if (! spec->autocfg.line_outs)
return 0; /* can't find valid pin config */
+#if 0 /* FIXME: temporarily disabled */
/* If we have no real line-out pin and multiple hp-outs, HPs should
* be set up as multi-channel outputs.
*/
@@ -3526,6 +3536,7 @@ static int stac92xx_parse_auto_config(struct hda_codec *codec, hda_nid_t dig_out
spec->autocfg.line_out_type = AUTO_PIN_HP_OUT;
spec->autocfg.hp_outs = 0;
}
+#endif /* FIXME: temporarily disabled */
if (spec->autocfg.mono_out_pin) {
int dir = get_wcaps(codec, spec->autocfg.mono_out_pin) &
(AC_WCAP_OUT_AMP | AC_WCAP_IN_AMP);
@@ -4980,7 +4991,7 @@ again:
case STAC_DELL_M4_3:
spec->num_dmics = 1;
spec->num_smuxes = 0;
- spec->num_dmuxes = 0;
+ spec->num_dmuxes = 1;
break;
default:
spec->num_dmics = STAC92HD71BXX_NUM_DMICS;
diff --git a/sound/pci/mixart/mixart.c b/sound/pci/mixart/mixart.c
index f23a73577c2..bb162507fe6 100644
--- a/sound/pci/mixart/mixart.c
+++ b/sound/pci/mixart/mixart.c
@@ -607,6 +607,7 @@ static int snd_mixart_hw_params(struct snd_pcm_substream *subs,
/* set the format to the board */
err = mixart_set_format(stream, format);
if(err < 0) {
+ mutex_unlock(&mgr->setup_mutex);
return err;
}
diff --git a/sound/pci/oxygen/virtuoso.c b/sound/pci/oxygen/virtuoso.c
index 18c7c91786b..6c870c12a17 100644
--- a/sound/pci/oxygen/virtuoso.c
+++ b/sound/pci/oxygen/virtuoso.c
@@ -26,7 +26,7 @@
* SPI 0 -> 1st PCM1796 (front)
* SPI 1 -> 2nd PCM1796 (surround)
* SPI 2 -> 3rd PCM1796 (center/LFE)
- * SPI 4 -> 4th PCM1796 (back) and EEPROM self-destruct (do not use!)
+ * SPI 4 -> 4th PCM1796 (back)
*
* GPIO 2 -> M0 of CS5381
* GPIO 3 -> M1 of CS5381
@@ -207,12 +207,6 @@ static void xonar_gpio_changed(struct oxygen *chip);
static inline void pcm1796_write_spi(struct oxygen *chip, unsigned int codec,
u8 reg, u8 value)
{
- /*
- * We don't want to do writes on SPI 4 because the EEPROM, which shares
- * the same pin, might get confused and broken. We'd better take care
- * that the driver works with the default register values ...
- */
-#if 0
/* maps ALSA channel pair number to SPI output */
static const u8 codec_map[4] = {
0, 1, 2, 4
@@ -223,7 +217,6 @@ static inline void pcm1796_write_spi(struct oxygen *chip, unsigned int codec,
(codec_map[codec] << OXYGEN_SPI_CODEC_SHIFT) |
OXYGEN_SPI_CEN_LATCH_CLOCK_HI,
(reg << 8) | value);
-#endif
}
static inline void pcm1796_write_i2c(struct oxygen *chip, unsigned int codec,
@@ -757,9 +750,6 @@ static const DECLARE_TLV_DB_SCALE(cs4362a_db_scale, -12700, 100, 0);
static int xonar_d2_control_filter(struct snd_kcontrol_new *template)
{
- if (!strncmp(template->name, "Master Playback ", 16))
- /* disable volume/mute because they would require SPI writes */
- return 1;
if (!strncmp(template->name, "CD Capture ", 11))
/* CD in is actually connected to the video in pin */
template->private_value ^= AC97_CD ^ AC97_VIDEO;
@@ -850,8 +840,9 @@ static const struct oxygen_model model_xonar_d2 = {
.dac_volume_min = 0x0f,
.dac_volume_max = 0xff,
.misc_flags = OXYGEN_MISC_MIDI,
- .function_flags = OXYGEN_FUNCTION_SPI,
- .dac_i2s_format = OXYGEN_I2S_FORMAT_I2S,
+ .function_flags = OXYGEN_FUNCTION_SPI |
+ OXYGEN_FUNCTION_ENABLE_SPI_4_5,
+ .dac_i2s_format = OXYGEN_I2S_FORMAT_LJUST,
.adc_i2s_format = OXYGEN_I2S_FORMAT_LJUST,
};
diff --git a/sound/pci/pcxhr/pcxhr.h b/sound/pci/pcxhr/pcxhr.h
index 84131a916c9..69d87dee699 100644
--- a/sound/pci/pcxhr/pcxhr.h
+++ b/sound/pci/pcxhr/pcxhr.h
@@ -97,12 +97,12 @@ struct pcxhr_mgr {
int capture_chips;
int fw_file_set;
int firmware_num;
- int is_hr_stereo:1;
- int board_has_aes1:1; /* if 1 board has AES1 plug and SRC */
- int board_has_analog:1; /* if 0 the board is digital only */
- int board_has_mic:1; /* if 1 the board has microphone input */
- int board_aes_in_192k:1;/* if 1 the aes input plugs do support 192kHz */
- int mono_capture:1; /* if 1 the board does mono capture */
+ unsigned int is_hr_stereo:1;
+ unsigned int board_has_aes1:1; /* if 1 board has AES1 plug and SRC */
+ unsigned int board_has_analog:1; /* if 0 the board is digital only */
+ unsigned int board_has_mic:1; /* if 1 the board has microphone input */
+ unsigned int board_aes_in_192k:1;/* if 1 the aes input plugs do support 192kHz */
+ unsigned int mono_capture:1; /* if 1 the board does mono capture */
struct snd_dma_buffer hostport;
diff --git a/sound/soc/codecs/tlv320aic3x.c b/sound/soc/codecs/tlv320aic3x.c
index b47a749c5ea..aea0cb72d80 100644
--- a/sound/soc/codecs/tlv320aic3x.c
+++ b/sound/soc/codecs/tlv320aic3x.c
@@ -165,10 +165,13 @@ static int snd_soc_dapm_put_volsw_aic3x(struct snd_kcontrol *kcontrol,
struct snd_ctl_elem_value *ucontrol)
{
struct snd_soc_dapm_widget *widget = snd_kcontrol_chip(kcontrol);
- int reg = kcontrol->private_value & 0xff;
- int shift = (kcontrol->private_value >> 8) & 0x0f;
- int mask = (kcontrol->private_value >> 16) & 0xff;
- int invert = (kcontrol->private_value >> 24) & 0x01;
+ struct soc_mixer_control *mc =
+ (struct soc_mixer_control *)kcontrol->private_value;
+ unsigned int reg = mc->reg;
+ unsigned int shift = mc->shift;
+ int max = mc->max;
+ unsigned int mask = (1 << fls(max)) - 1;
+ unsigned int invert = mc->invert;
unsigned short val, val_mask;
int ret;
struct snd_soc_dapm_path *path;
diff --git a/sound/soc/codecs/wm8990.c b/sound/soc/codecs/wm8990.c
index 1cbb7b9b51c..a5731faa150 100644
--- a/sound/soc/codecs/wm8990.c
+++ b/sound/soc/codecs/wm8990.c
@@ -176,7 +176,9 @@ static int wm899x_outpga_put_volsw_vu(struct snd_kcontrol *kcontrol,
struct snd_ctl_elem_value *ucontrol)
{
struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol);
- int reg = kcontrol->private_value & 0xff;
+ struct soc_mixer_control *mc =
+ (struct soc_mixer_control *)kcontrol->private_value;
+ int reg = mc->reg;
int ret;
u16 val;
diff --git a/sound/soc/omap/sdp3430.c b/sound/soc/omap/sdp3430.c
index ad97836818b..e226fa75669 100644
--- a/sound/soc/omap/sdp3430.c
+++ b/sound/soc/omap/sdp3430.c
@@ -91,7 +91,7 @@ static struct snd_soc_dai_link sdp3430_dai = {
};
/* Audio machine driver */
-static struct snd_soc_machine snd_soc_machine_sdp3430 = {
+static struct snd_soc_card snd_soc_sdp3430 = {
.name = "SDP3430",
.platform = &omap_soc_platform,
.dai_link = &sdp3430_dai,
@@ -100,7 +100,7 @@ static struct snd_soc_machine snd_soc_machine_sdp3430 = {
/* Audio subsystem */
static struct snd_soc_device sdp3430_snd_devdata = {
- .machine = &snd_soc_machine_sdp3430,
+ .card = &snd_soc_sdp3430,
.codec_dev = &soc_codec_dev_twl4030,
};
diff --git a/sound/soc/soc-core.c b/sound/soc/soc-core.c
index 55fdb4abb17..ec3f8bb4b51 100644
--- a/sound/soc/soc-core.c
+++ b/sound/soc/soc-core.c
@@ -1385,7 +1385,10 @@ int snd_soc_init_card(struct snd_soc_device *socdev)
mutex_lock(&codec->mutex);
#ifdef CONFIG_SND_SOC_AC97_BUS
- if (ac97) {
+ /* Only instantiate AC97 if not already done by the adaptor
+ * for the generic AC97 subsystem.
+ */
+ if (ac97 && strcmp(codec->name, "AC97") != 0) {
ret = soc_ac97_dev_register(codec);
if (ret < 0) {
printk(KERN_ERR "asoc: AC97 device register failed\n");
diff --git a/sound/usb/usbaudio.c b/sound/usb/usbaudio.c
index c709b956322..19e37451c21 100644
--- a/sound/usb/usbaudio.c
+++ b/sound/usb/usbaudio.c
@@ -2524,7 +2524,6 @@ static int parse_audio_format_rates(struct snd_usb_audio *chip, struct audioform
* build the rate table and bitmap flags
*/
int r, idx;
- unsigned int nonzero_rates = 0;
fp->rate_table = kmalloc(sizeof(int) * nr_rates, GFP_KERNEL);
if (fp->rate_table == NULL) {
@@ -2532,24 +2531,27 @@ static int parse_audio_format_rates(struct snd_usb_audio *chip, struct audioform
return -1;
}
- fp->nr_rates = nr_rates;
- fp->rate_min = fp->rate_max = combine_triple(&fmt[8]);
+ fp->nr_rates = 0;
+ fp->rate_min = fp->rate_max = 0;
for (r = 0, idx = offset + 1; r < nr_rates; r++, idx += 3) {
unsigned int rate = combine_triple(&fmt[idx]);
+ if (!rate)
+ continue;
/* C-Media CM6501 mislabels its 96 kHz altsetting */
if (rate == 48000 && nr_rates == 1 &&
- chip->usb_id == USB_ID(0x0d8c, 0x0201) &&
+ (chip->usb_id == USB_ID(0x0d8c, 0x0201) ||
+ chip->usb_id == USB_ID(0x0d8c, 0x0102)) &&
fp->altsetting == 5 && fp->maxpacksize == 392)
rate = 96000;
- fp->rate_table[r] = rate;
- nonzero_rates |= rate;
- if (rate < fp->rate_min)
+ fp->rate_table[fp->nr_rates] = rate;
+ if (!fp->rate_min || rate < fp->rate_min)
fp->rate_min = rate;
- else if (rate > fp->rate_max)
+ if (!fp->rate_max || rate > fp->rate_max)
fp->rate_max = rate;
fp->rates |= snd_pcm_rate_to_rate_bit(rate);
+ fp->nr_rates++;
}
- if (!nonzero_rates) {
+ if (!fp->nr_rates) {
hwc_debug("All rates were zero. Skipping format!\n");
return -1;
}
@@ -2966,6 +2968,7 @@ static int create_fixed_stream_quirk(struct snd_usb_audio *chip,
return -EINVAL;
}
alts = &iface->altsetting[fp->altset_idx];
+ fp->maxpacksize = le16_to_cpu(get_endpoint(alts, 0)->wMaxPacketSize);
usb_set_interface(chip->dev, fp->iface, 0);
init_usb_pitch(chip->dev, fp->iface, alts, fp);
init_usb_sample_rate(chip->dev, fp->iface, alts, fp, fp->rate_max);
diff --git a/sound/usb/usbmidi.c b/sound/usb/usbmidi.c
index 320641ab5be..26bad373fe6 100644
--- a/sound/usb/usbmidi.c
+++ b/sound/usb/usbmidi.c
@@ -1625,6 +1625,7 @@ static int snd_usbmidi_create_endpoints_midiman(struct snd_usb_midi* umidi,
}
ep_info.out_ep = get_endpoint(hostif, 2)->bEndpointAddress & USB_ENDPOINT_NUMBER_MASK;
+ ep_info.out_interval = 0;
ep_info.out_cables = endpoint->out_cables & 0x5555;
err = snd_usbmidi_out_endpoint_create(umidi, &ep_info, &umidi->endpoints[0]);
if (err < 0)