diff options
Diffstat (limited to 'sound')
-rw-r--r-- | sound/core/init.c | 9 | ||||
-rw-r--r-- | sound/core/jack.c | 21 | ||||
-rw-r--r-- | sound/core/seq/seq_ump_convert.c | 42 | ||||
-rw-r--r-- | sound/core/ump.c | 15 | ||||
-rw-r--r-- | sound/core/ump_convert.c | 1 | ||||
-rw-r--r-- | sound/hda/intel-dsp-config.c | 8 | ||||
-rw-r--r-- | sound/pci/hda/patch_realtek.c | 2 |
7 files changed, 80 insertions, 18 deletions
diff --git a/sound/core/init.c b/sound/core/init.c index 4e52bbe32786..b9b708cf980d 100644 --- a/sound/core/init.c +++ b/sound/core/init.c @@ -537,6 +537,11 @@ void snd_card_disconnect(struct snd_card *card) synchronize_irq(card->sync_irq); snd_info_card_disconnect(card); +#ifdef CONFIG_SND_DEBUG + debugfs_remove(card->debugfs_root); + card->debugfs_root = NULL; +#endif + if (card->registered) { device_del(&card->card_dev); card->registered = false; @@ -586,10 +591,6 @@ static int snd_card_do_free(struct snd_card *card) dev_warn(card->dev, "unable to free card info\n"); /* Not fatal error */ } -#ifdef CONFIG_SND_DEBUG - debugfs_remove(card->debugfs_root); - card->debugfs_root = NULL; -#endif if (card->release_completion) complete(card->release_completion); if (!card->managed) diff --git a/sound/core/jack.c b/sound/core/jack.c index e08b2c4fbd1a..e4bcecdf89b7 100644 --- a/sound/core/jack.c +++ b/sound/core/jack.c @@ -37,11 +37,15 @@ static const int jack_switch_types[SND_JACK_SWITCH_TYPES] = { }; #endif /* CONFIG_SND_JACK_INPUT_DEV */ +static void snd_jack_remove_debugfs(struct snd_jack *jack); + static int snd_jack_dev_disconnect(struct snd_device *device) { -#ifdef CONFIG_SND_JACK_INPUT_DEV struct snd_jack *jack = device->device_data; + snd_jack_remove_debugfs(jack); + +#ifdef CONFIG_SND_JACK_INPUT_DEV guard(mutex)(&jack->input_dev_lock); if (!jack->input_dev) return 0; @@ -381,10 +385,14 @@ static int snd_jack_debugfs_add_inject_node(struct snd_jack *jack, return 0; } -static void snd_jack_debugfs_clear_inject_node(struct snd_jack_kctl *jack_kctl) +static void snd_jack_remove_debugfs(struct snd_jack *jack) { - debugfs_remove(jack_kctl->jack_debugfs_root); - jack_kctl->jack_debugfs_root = NULL; + struct snd_jack_kctl *jack_kctl; + + list_for_each_entry(jack_kctl, &jack->kctl_list, list) { + debugfs_remove(jack_kctl->jack_debugfs_root); + jack_kctl->jack_debugfs_root = NULL; + } } #else /* CONFIG_SND_JACK_INJECTION_DEBUG */ static int snd_jack_debugfs_add_inject_node(struct snd_jack *jack, @@ -393,7 +401,7 @@ static int snd_jack_debugfs_add_inject_node(struct snd_jack *jack, return 0; } -static void snd_jack_debugfs_clear_inject_node(struct snd_jack_kctl *jack_kctl) +static void snd_jack_remove_debugfs(struct snd_jack *jack) { } #endif /* CONFIG_SND_JACK_INJECTION_DEBUG */ @@ -404,7 +412,6 @@ static void snd_jack_kctl_private_free(struct snd_kcontrol *kctl) jack_kctl = kctl->private_data; if (jack_kctl) { - snd_jack_debugfs_clear_inject_node(jack_kctl); list_del(&jack_kctl->list); kfree(jack_kctl); } @@ -497,8 +504,8 @@ int snd_jack_new(struct snd_card *card, const char *id, int type, .dev_free = snd_jack_dev_free, #ifdef CONFIG_SND_JACK_INPUT_DEV .dev_register = snd_jack_dev_register, - .dev_disconnect = snd_jack_dev_disconnect, #endif /* CONFIG_SND_JACK_INPUT_DEV */ + .dev_disconnect = snd_jack_dev_disconnect, }; if (initial_kctl) { diff --git a/sound/core/seq/seq_ump_convert.c b/sound/core/seq/seq_ump_convert.c index ee6ac649df83..f0f332017e66 100644 --- a/sound/core/seq/seq_ump_convert.c +++ b/sound/core/seq/seq_ump_convert.c @@ -368,6 +368,7 @@ static int cvt_ump_midi1_to_midi2(struct snd_seq_client *dest, struct snd_seq_ump_event ev_cvt; const union snd_ump_midi1_msg *midi1 = (const union snd_ump_midi1_msg *)event->ump; union snd_ump_midi2_msg *midi2 = (union snd_ump_midi2_msg *)ev_cvt.ump; + struct snd_seq_ump_midi2_bank *cc; ev_cvt = *event; memset(&ev_cvt.ump, 0, sizeof(ev_cvt.ump)); @@ -387,11 +388,29 @@ static int cvt_ump_midi1_to_midi2(struct snd_seq_client *dest, midi2->paf.data = upscale_7_to_32bit(midi1->paf.data); break; case UMP_MSG_STATUS_CC: + cc = &dest_port->midi2_bank[midi1->note.channel]; + switch (midi1->cc.index) { + case UMP_CC_BANK_SELECT: + cc->bank_set = 1; + cc->cc_bank_msb = midi1->cc.data; + return 0; // skip + case UMP_CC_BANK_SELECT_LSB: + cc->bank_set = 1; + cc->cc_bank_lsb = midi1->cc.data; + return 0; // skip + } midi2->cc.index = midi1->cc.index; midi2->cc.data = upscale_7_to_32bit(midi1->cc.data); break; case UMP_MSG_STATUS_PROGRAM: midi2->pg.program = midi1->pg.program; + cc = &dest_port->midi2_bank[midi1->note.channel]; + if (cc->bank_set) { + midi2->pg.bank_valid = 1; + midi2->pg.bank_msb = cc->cc_bank_msb; + midi2->pg.bank_lsb = cc->cc_bank_lsb; + cc->bank_set = 0; + } break; case UMP_MSG_STATUS_CHANNEL_PRESSURE: midi2->caf.data = upscale_7_to_32bit(midi1->caf.data); @@ -419,6 +438,7 @@ static int cvt_ump_midi2_to_midi1(struct snd_seq_client *dest, struct snd_seq_ump_event ev_cvt; union snd_ump_midi1_msg *midi1 = (union snd_ump_midi1_msg *)ev_cvt.ump; const union snd_ump_midi2_msg *midi2 = (const union snd_ump_midi2_msg *)event->ump; + int err; u16 v; ev_cvt = *event; @@ -443,6 +463,24 @@ static int cvt_ump_midi2_to_midi1(struct snd_seq_client *dest, midi1->cc.data = downscale_32_to_7bit(midi2->cc.data); break; case UMP_MSG_STATUS_PROGRAM: + if (midi2->pg.bank_valid) { + midi1->cc.status = UMP_MSG_STATUS_CC; + midi1->cc.index = UMP_CC_BANK_SELECT; + midi1->cc.data = midi2->pg.bank_msb; + err = __snd_seq_deliver_single_event(dest, dest_port, + (struct snd_seq_event *)&ev_cvt, + atomic, hop); + if (err < 0) + return err; + midi1->cc.index = UMP_CC_BANK_SELECT_LSB; + midi1->cc.data = midi2->pg.bank_lsb; + err = __snd_seq_deliver_single_event(dest, dest_port, + (struct snd_seq_event *)&ev_cvt, + atomic, hop); + if (err < 0) + return err; + midi1->note.status = midi2->note.status; + } midi1->pg.program = midi2->pg.program; break; case UMP_MSG_STATUS_CHANNEL_PRESSURE: @@ -691,6 +729,7 @@ static int system_ev_to_ump_midi1(const struct snd_seq_event *event, union snd_ump_midi1_msg *data, unsigned char status) { + data->system.type = UMP_MSG_TYPE_SYSTEM; // override data->system.status = status; return 1; } @@ -701,6 +740,7 @@ static int system_1p_ev_to_ump_midi1(const struct snd_seq_event *event, union snd_ump_midi1_msg *data, unsigned char status) { + data->system.type = UMP_MSG_TYPE_SYSTEM; // override data->system.status = status; data->system.parm1 = event->data.control.value & 0x7f; return 1; @@ -712,6 +752,7 @@ static int system_2p_ev_to_ump_midi1(const struct snd_seq_event *event, union snd_ump_midi1_msg *data, unsigned char status) { + data->system.type = UMP_MSG_TYPE_SYSTEM; // override data->system.status = status; data->system.parm1 = (event->data.control.value >> 7) & 0x7f; data->system.parm2 = event->data.control.value & 0x7f; @@ -854,7 +895,6 @@ static int pgm_ev_to_ump_midi2(const struct snd_seq_event *event, data->pg.bank_msb = cc->cc_bank_msb; data->pg.bank_lsb = cc->cc_bank_lsb; cc->bank_set = 0; - cc->cc_bank_msb = cc->cc_bank_lsb = 0; } return 1; } diff --git a/sound/core/ump.c b/sound/core/ump.c index fd6a68a54278..3f61220c23b4 100644 --- a/sound/core/ump.c +++ b/sound/core/ump.c @@ -685,10 +685,17 @@ static void seq_notify_protocol(struct snd_ump_endpoint *ump) */ int snd_ump_switch_protocol(struct snd_ump_endpoint *ump, unsigned int protocol) { + unsigned int type; + protocol &= ump->info.protocol_caps; if (protocol == ump->info.protocol) return 0; + type = protocol & SNDRV_UMP_EP_INFO_PROTO_MIDI_MASK; + if (type != SNDRV_UMP_EP_INFO_PROTO_MIDI1 && + type != SNDRV_UMP_EP_INFO_PROTO_MIDI2) + return 0; + ump->info.protocol = protocol; ump_dbg(ump, "New protocol = %x (caps = %x)\n", protocol, ump->info.protocol_caps); @@ -960,6 +967,14 @@ int snd_ump_parse_endpoint(struct snd_ump_endpoint *ump) if (err < 0) ump_dbg(ump, "Unable to get UMP EP stream config\n"); + /* If no protocol is set by some reason, assume the valid one */ + if (!(ump->info.protocol & SNDRV_UMP_EP_INFO_PROTO_MIDI_MASK)) { + if (ump->info.protocol_caps & SNDRV_UMP_EP_INFO_PROTO_MIDI2) + ump->info.protocol |= SNDRV_UMP_EP_INFO_PROTO_MIDI2; + else if (ump->info.protocol_caps & SNDRV_UMP_EP_INFO_PROTO_MIDI1) + ump->info.protocol |= SNDRV_UMP_EP_INFO_PROTO_MIDI1; + } + /* Query and create blocks from Function Blocks */ for (blk = 0; blk < ump->info.num_blocks; blk++) { err = create_block_from_fb_info(ump, blk); diff --git a/sound/core/ump_convert.c b/sound/core/ump_convert.c index de04799fdb69..f67c44c83fde 100644 --- a/sound/core/ump_convert.c +++ b/sound/core/ump_convert.c @@ -404,7 +404,6 @@ static int cvt_legacy_cmd_to_ump(struct ump_cvt_to_ump *cvt, midi2->pg.bank_msb = cc->cc_bank_msb; midi2->pg.bank_lsb = cc->cc_bank_lsb; cc->bank_set = 0; - cc->cc_bank_msb = cc->cc_bank_lsb = 0; } break; case UMP_MSG_STATUS_CHANNEL_PRESSURE: diff --git a/sound/hda/intel-dsp-config.c b/sound/hda/intel-dsp-config.c index cfdb1b73c88c..537863447358 100644 --- a/sound/hda/intel-dsp-config.c +++ b/sound/hda/intel-dsp-config.c @@ -668,7 +668,7 @@ int snd_intel_dsp_driver_probe(struct pci_dev *pci) return SND_INTEL_DSP_DRIVER_LEGACY; } - dev_info(&pci->dev, "DSP detected with PCI class/subclass/prog-if info 0x%06x\n", pci->class); + dev_dbg(&pci->dev, "DSP detected with PCI class/subclass/prog-if info 0x%06x\n", pci->class); /* find the configuration for the specific device */ cfg = snd_intel_dsp_find_config(pci, config_table, ARRAY_SIZE(config_table)); @@ -678,12 +678,12 @@ int snd_intel_dsp_driver_probe(struct pci_dev *pci) if (cfg->flags & FLAG_SOF) { if (cfg->flags & FLAG_SOF_ONLY_IF_SOUNDWIRE && snd_intel_dsp_check_soundwire(pci) > 0) { - dev_info(&pci->dev, "SoundWire enabled on CannonLake+ platform, using SOF driver\n"); + dev_info_once(&pci->dev, "SoundWire enabled on CannonLake+ platform, using SOF driver\n"); return SND_INTEL_DSP_DRIVER_SOF; } if (cfg->flags & FLAG_SOF_ONLY_IF_DMIC && snd_intel_dsp_check_dmic(pci)) { - dev_info(&pci->dev, "Digital mics found on Skylake+ platform, using SOF driver\n"); + dev_info_once(&pci->dev, "Digital mics found on Skylake+ platform, using SOF driver\n"); return SND_INTEL_DSP_DRIVER_SOF; } if (!(cfg->flags & FLAG_SOF_ONLY_IF_DMIC_OR_SOUNDWIRE)) @@ -694,7 +694,7 @@ int snd_intel_dsp_driver_probe(struct pci_dev *pci) if (cfg->flags & FLAG_SST) { if (cfg->flags & FLAG_SST_ONLY_IF_DMIC) { if (snd_intel_dsp_check_dmic(pci)) { - dev_info(&pci->dev, "Digital mics found on Skylake+ platform, using SST driver\n"); + dev_info_once(&pci->dev, "Digital mics found on Skylake+ platform, using SST driver\n"); return SND_INTEL_DSP_DRIVER_SST; } } else { diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index e3c0b9d5552d..aa76d1c88589 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -10310,7 +10310,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x1043, 0x3030, "ASUS ZN270IE", ALC256_FIXUP_ASUS_AIO_GPIO2), SND_PCI_QUIRK(0x1043, 0x3a20, "ASUS G614JZR", ALC245_FIXUP_CS35L41_SPI_2), SND_PCI_QUIRK(0x1043, 0x3a30, "ASUS G814JVR/JIR", ALC245_FIXUP_CS35L41_SPI_2), - SND_PCI_QUIRK(0x1043, 0x3a40, "ASUS G814JZR", ALC245_FIXUP_CS35L41_SPI_2), + SND_PCI_QUIRK(0x1043, 0x3a40, "ASUS G814JZR", ALC285_FIXUP_ASUS_SPI_REAR_SPEAKERS), SND_PCI_QUIRK(0x1043, 0x3a50, "ASUS G834JYR/JZR", ALC245_FIXUP_CS35L41_SPI_2), SND_PCI_QUIRK(0x1043, 0x3a60, "ASUS G634JYR/JZR", ALC285_FIXUP_ASUS_SPI_REAR_SPEAKERS), SND_PCI_QUIRK(0x1043, 0x831a, "ASUS P901", ALC269_FIXUP_STEREO_DMIC), |