Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'sound-fix-6.3-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound

Pull sound fixes from Takashi Iwai:
"A collection of various small fixes that have been gathered since the
last PR.

The majority of changes are for ASoC, and there is a small change in
ASoC PCM core, but the rest are all for driver- specific fixes /
quirks / updates"

* tag 'sound-fix-6.3-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/tiwai/sound: (32 commits)
ALSA: ice1712: Delete unreachable code in aureon_add_controls()
ALSA: ice1712: Do not left ice->gpio_mutex locked in aureon_add_controls()
ALSA: hda/realtek: Add quirk for HP EliteDesk 800 G6 Tower PC
ALSA: hda/realtek: Improve support for Dell Precision 3260
ASoC: mediatek: mt8195: add missing initialization
ASoC: mediatek: mt8188: add missing initialization
ASoC: amd: yc: Add DMI entries to support HP OMEN 16-n0xxx (8A43)
ASoC: zl38060 add gpiolib dependency
ASoC: sam9g20ek: Disable capture unless building with microphone input
ASoC: mt8192: Fix range for sidetone positive gain
ASoC: mt8192: Report an error if when an invalid sidetone gain is written
ASoC: mt8192: Fix event generation for controls
ASoC: mt8192: Remove spammy log messages
ASoC: mchp-pdmc: fix poc noise at capture startup
ASoC: dt-bindings: sama7g5-pdmc: add microchip,startup-delay-us binding
ASoC: soc-pcm: add option to start DMA after DAI
ASoC: mt8183: Fix event generation for I2S DAI operations
ASoC: mt8183: Remove spammy logging from I2S DAI driver
ASoC: mt6358: Remove undefined HPx Mux enumeration values
ASoC: mt6358: Validate Wake on Voice 2 writes
...

+263 -152
+1
Documentation/devicetree/bindings/sound/apple,mca.yaml
··· 23 23 - enum: 24 24 - apple,t6000-mca 25 25 - apple,t8103-mca 26 + - apple,t8112-mca 26 27 - const: apple,mca 27 28 28 29 reg:
+6
Documentation/devicetree/bindings/sound/microchip,sama7g5-pdmc.yaml
··· 67 67 maxItems: 4 68 68 uniqueItems: true 69 69 70 + microchip,startup-delay-us: 71 + description: | 72 + Specifies the delay in microseconds that needs to be applied after 73 + enabling the PDMC microphones to avoid unwanted noise due to microphones 74 + not being ready. 75 + 70 76 required: 71 77 - compatible 72 78 - reg
+2
include/sound/soc-component.h
··· 190 190 bool use_dai_pcm_id; /* use DAI link PCM ID as PCM device number */ 191 191 int be_pcm_base; /* base device ID for all BE PCMs */ 192 192 193 + unsigned int start_dma_last; 194 + 193 195 #ifdef CONFIG_DEBUG_FS 194 196 const char *debugfs_prefix; 195 197 #endif
+2
sound/pci/hda/patch_realtek.c
··· 9260 9260 SND_PCI_QUIRK(0x1028, 0x0a62, "Dell Precision 5560", ALC289_FIXUP_DUAL_SPK), 9261 9261 SND_PCI_QUIRK(0x1028, 0x0a9d, "Dell Latitude 5430", ALC269_FIXUP_DELL4_MIC_NO_PRESENCE), 9262 9262 SND_PCI_QUIRK(0x1028, 0x0a9e, "Dell Latitude 5430", ALC269_FIXUP_DELL4_MIC_NO_PRESENCE), 9263 + SND_PCI_QUIRK(0x1028, 0x0ac9, "Dell Precision 3260", ALC295_FIXUP_CHROME_BOOK), 9263 9264 SND_PCI_QUIRK(0x1028, 0x0b19, "Dell XPS 15 9520", ALC289_FIXUP_DUAL_SPK), 9264 9265 SND_PCI_QUIRK(0x1028, 0x0b1a, "Dell Precision 5570", ALC289_FIXUP_DUAL_SPK), 9265 9266 SND_PCI_QUIRK(0x1028, 0x0b37, "Dell Inspiron 16 Plus 7620 2-in-1", ALC295_FIXUP_DELL_INSPIRON_TOP_SPEAKERS), ··· 11618 11617 SND_PCI_QUIRK(0x1028, 0x0698, "Dell", ALC668_FIXUP_DELL_MIC_NO_PRESENCE), 11619 11618 SND_PCI_QUIRK(0x1028, 0x069f, "Dell", ALC668_FIXUP_DELL_MIC_NO_PRESENCE), 11620 11619 SND_PCI_QUIRK(0x103c, 0x1632, "HP RP5800", ALC662_FIXUP_HP_RP5800), 11620 + SND_PCI_QUIRK(0x103c, 0x870c, "HP", ALC897_FIXUP_HP_HSMIC_VERB), 11621 11621 SND_PCI_QUIRK(0x103c, 0x8719, "HP", ALC897_FIXUP_HP_HSMIC_VERB), 11622 11622 SND_PCI_QUIRK(0x103c, 0x873e, "HP", ALC671_FIXUP_HP_HEADSET_MIC2), 11623 11623 SND_PCI_QUIRK(0x103c, 0x877e, "HP 288 Pro G6", ALC671_FIXUP_HP_HEADSET_MIC2),
+1 -5
sound/pci/ice1712/aureon.c
··· 1892 1892 unsigned char id; 1893 1893 snd_ice1712_save_gpio_status(ice); 1894 1894 id = aureon_cs8415_get(ice, CS8415_ID); 1895 + snd_ice1712_restore_gpio_status(ice); 1895 1896 if (id != 0x41) 1896 1897 dev_info(ice->card->dev, 1897 1898 "No CS8415 chip. Skipping CS8415 controls.\n"); 1898 - else if ((id & 0x0F) != 0x01) 1899 - dev_info(ice->card->dev, 1900 - "Detected unsupported CS8415 rev. (%c)\n", 1901 - (char)((id & 0x0F) + 'A' - 1)); 1902 1899 else { 1903 1900 for (i = 0; i < ARRAY_SIZE(cs8415_controls); i++) { 1904 1901 struct snd_kcontrol *kctl; ··· 1906 1909 kctl->id.device = ice->pcm->device; 1907 1910 } 1908 1911 } 1909 - snd_ice1712_restore_gpio_status(ice); 1910 1912 } 1911 1913 1912 1914 return 0;
+14
sound/soc/amd/yc/acp6x-mach.c
··· 255 255 DMI_MATCH(DMI_PRODUCT_NAME, "15NBC1011"), 256 256 } 257 257 }, 258 + { 259 + .driver_data = &acp6x_card, 260 + .matches = { 261 + DMI_MATCH(DMI_BOARD_VENDOR, "HP"), 262 + DMI_MATCH(DMI_PRODUCT_NAME, "OMEN by HP Gaming Laptop 16z-n000"), 263 + } 264 + }, 265 + { 266 + .driver_data = &acp6x_card, 267 + .matches = { 268 + DMI_MATCH(DMI_BOARD_VENDOR, "HP"), 269 + DMI_MATCH(DMI_BOARD_NAME, "8A43"), 270 + } 271 + }, 258 272 {} 259 273 }; 260 274
+23 -8
sound/soc/apple/mca.c
··· 101 101 #define SERDES_CONF_UNK3 BIT(14) 102 102 #define SERDES_CONF_NO_DATA_FEEDBACK BIT(15) 103 103 #define SERDES_CONF_SYNC_SEL GENMASK(18, 16) 104 - #define SERDES_CONF_SOME_RST BIT(19) 105 104 #define REG_TX_SERDES_BITSTART 0x08 106 105 #define REG_RX_SERDES_BITSTART 0x0c 107 106 #define REG_TX_SERDES_SLOTMASK 0x0c ··· 202 203 case SNDRV_PCM_TRIGGER_START: 203 204 case SNDRV_PCM_TRIGGER_RESUME: 204 205 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: 206 + mca_modify(cl, serdes_conf, SERDES_CONF_SYNC_SEL, 207 + FIELD_PREP(SERDES_CONF_SYNC_SEL, 0)); 208 + mca_modify(cl, serdes_conf, SERDES_CONF_SYNC_SEL, 209 + FIELD_PREP(SERDES_CONF_SYNC_SEL, 7)); 205 210 mca_modify(cl, serdes_unit + REG_SERDES_STATUS, 206 211 SERDES_STATUS_EN | SERDES_STATUS_RST, 207 212 SERDES_STATUS_RST); 208 - mca_modify(cl, serdes_conf, SERDES_CONF_SOME_RST, 209 - SERDES_CONF_SOME_RST); 210 - readl_relaxed(cl->base + serdes_conf); 211 - mca_modify(cl, serdes_conf, SERDES_STATUS_RST, 0); 212 - WARN_ON(readl_relaxed(cl->base + REG_SERDES_STATUS) & 213 + /* 214 + * Experiments suggest that it takes at most ~1 us 215 + * for the bit to clear, so wait 2 us for good measure. 216 + */ 217 + udelay(2); 218 + WARN_ON(readl_relaxed(cl->base + serdes_unit + REG_SERDES_STATUS) & 213 219 SERDES_STATUS_RST); 220 + mca_modify(cl, serdes_conf, SERDES_CONF_SYNC_SEL, 221 + FIELD_PREP(SERDES_CONF_SYNC_SEL, 0)); 222 + mca_modify(cl, serdes_conf, SERDES_CONF_SYNC_SEL, 223 + FIELD_PREP(SERDES_CONF_SYNC_SEL, cl->no + 1)); 214 224 break; 215 225 default: 216 226 break; ··· 950 942 chan = mca_request_dma_channel(cl, i); 951 943 952 944 if (IS_ERR_OR_NULL(chan)) { 945 + mca_pcm_free(component, rtd->pcm); 946 + 947 + if (chan && PTR_ERR(chan) == -EPROBE_DEFER) 948 + return PTR_ERR(chan); 949 + 953 950 dev_err(component->dev, "unable to obtain DMA channel (stream %d cluster %d): %pe\n", 954 951 i, cl->no, chan); 955 - mca_pcm_free(component, rtd->pcm); 956 - return -EINVAL; 952 + 953 + if (!chan) 954 + return -EINVAL; 955 + return PTR_ERR(chan); 957 956 } 958 957 959 958 cl->dma_chans[i] = chan;
+48 -5
sound/soc/atmel/mchp-pdmc.c
··· 114 114 struct clk *gclk; 115 115 u32 pdmcen; 116 116 u32 suspend_irq; 117 + u32 startup_delay_us; 117 118 int mic_no; 118 119 int sinc_order; 119 120 bool audio_filter_en; ··· 426 425 .open = &mchp_pdmc_open, 427 426 .close = &mchp_pdmc_close, 428 427 .legacy_dai_naming = 1, 428 + .start_dma_last = 1, 429 429 }; 430 430 431 431 static const unsigned int mchp_pdmc_1mic[] = {1}; ··· 634 632 return 0; 635 633 } 636 634 635 + static void mchp_pdmc_noise_filter_workaround(struct mchp_pdmc *dd) 636 + { 637 + u32 tmp, steps = 16; 638 + 639 + /* 640 + * PDMC doesn't wait for microphones' startup time thus the acquisition 641 + * may start before the microphones are ready leading to poc noises at 642 + * the beginning of capture. To avoid this, we need to wait 50ms (in 643 + * normal startup procedure) or 150 ms (worst case after resume from sleep 644 + * states) after microphones are enabled and then clear the FIFOs (by 645 + * reading the RHR 16 times) and possible interrupts before continuing. 646 + * Also, for this to work the DMA needs to be started after interrupts 647 + * are enabled. 648 + */ 649 + usleep_range(dd->startup_delay_us, dd->startup_delay_us + 5); 650 + 651 + while (steps--) 652 + regmap_read(dd->regmap, MCHP_PDMC_RHR, &tmp); 653 + 654 + /* Clear interrupts. */ 655 + regmap_read(dd->regmap, MCHP_PDMC_ISR, &tmp); 656 + } 657 + 637 658 static int mchp_pdmc_trigger(struct snd_pcm_substream *substream, 638 659 int cmd, struct snd_soc_dai *dai) 639 660 { ··· 669 644 switch (cmd) { 670 645 case SNDRV_PCM_TRIGGER_RESUME: 671 646 case SNDRV_PCM_TRIGGER_START: 672 - /* Enable overrun and underrun error interrupts */ 673 - regmap_write(dd->regmap, MCHP_PDMC_IER, dd->suspend_irq | 674 - MCHP_PDMC_IR_RXOVR | MCHP_PDMC_IR_RXUDR); 675 - dd->suspend_irq = 0; 676 - fallthrough; 677 647 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: 678 648 snd_soc_component_update_bits(cpu, MCHP_PDMC_MR, 679 649 MCHP_PDMC_MR_PDMCEN_MASK, 680 650 dd->pdmcen); 651 + 652 + mchp_pdmc_noise_filter_workaround(dd); 653 + 654 + /* Enable interrupts. */ 655 + regmap_write(dd->regmap, MCHP_PDMC_IER, dd->suspend_irq | 656 + MCHP_PDMC_IR_RXOVR | MCHP_PDMC_IR_RXUDR); 657 + dd->suspend_irq = 0; 681 658 break; 682 659 case SNDRV_PCM_TRIGGER_SUSPEND: 683 660 regmap_read(dd->regmap, MCHP_PDMC_IMR, &dd->suspend_irq); ··· 823 796 case MCHP_PDMC_CFGR: 824 797 case MCHP_PDMC_IMR: 825 798 case MCHP_PDMC_ISR: 799 + case MCHP_PDMC_RHR: 826 800 case MCHP_PDMC_VER: 827 801 return true; 828 802 default: ··· 839 811 case MCHP_PDMC_CFGR: 840 812 case MCHP_PDMC_IER: 841 813 case MCHP_PDMC_IDR: 814 + return true; 815 + default: 816 + return false; 817 + } 818 + } 819 + 820 + static bool mchp_pdmc_volatile_reg(struct device *dev, unsigned int reg) 821 + { 822 + switch (reg) { 823 + case MCHP_PDMC_ISR: 824 + case MCHP_PDMC_RHR: 842 825 return true; 843 826 default: 844 827 return false; ··· 875 836 .readable_reg = mchp_pdmc_readable_reg, 876 837 .writeable_reg = mchp_pdmc_writeable_reg, 877 838 .precious_reg = mchp_pdmc_precious_reg, 839 + .volatile_reg = mchp_pdmc_volatile_reg, 878 840 .cache_type = REGCACHE_FLAT, 879 841 }; 880 842 ··· 957 917 dd->channel_mic_map[i].ds_pos = ds; 958 918 dd->channel_mic_map[i].clk_edge = edge; 959 919 } 920 + 921 + dd->startup_delay_us = 150000; 922 + of_property_read_u32(np, "microchip,startup-delay-us", &dd->startup_delay_us); 960 923 961 924 return 0; 962 925 }
+3
sound/soc/atmel/sam9g20_wm8731.c
··· 98 98 .init = at91sam9g20ek_wm8731_init, 99 99 .dai_fmt = SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | 100 100 SND_SOC_DAIFMT_CBP_CFP, 101 + #ifndef ENABLE_MIC_INPUT 102 + .playback_only = true, 103 + #endif 101 104 SND_SOC_DAILINK_REG(pcm), 102 105 }; 103 106
+1
sound/soc/codecs/Kconfig
··· 2103 2103 config SND_SOC_ZL38060 2104 2104 tristate "Microsemi ZL38060 Connected Home Audio Processor" 2105 2105 depends on SPI_MASTER 2106 + depends on GPIOLIB 2106 2107 select REGMAP 2107 2108 help 2108 2109 Support for ZL38060 Connected Home Audio Processor from Microsemi,
+1 -18
sound/soc/codecs/adau7118.c
··· 444 444 .endianness = 1, 445 445 }; 446 446 447 - static void adau7118_regulator_disable(void *data) 448 - { 449 - struct adau7118_data *st = data; 450 - int ret; 451 - /* 452 - * If we fail to disable DVDD, don't bother in trying IOVDD. We 453 - * actually don't want to be left in the situation where DVDD 454 - * is enabled and IOVDD is disabled. 455 - */ 456 - ret = regulator_disable(st->dvdd); 457 - if (ret) 458 - return; 459 - 460 - regulator_disable(st->iovdd); 461 - } 462 - 463 447 static int adau7118_regulator_setup(struct adau7118_data *st) 464 448 { 465 449 st->iovdd = devm_regulator_get(st->dev, "iovdd"); ··· 465 481 regcache_cache_only(st->map, true); 466 482 } 467 483 468 - return devm_add_action_or_reset(st->dev, adau7118_regulator_disable, 469 - st); 484 + return 0; 470 485 } 471 486 472 487 static int adau7118_parset_dt(const struct adau7118_data *st)
+34 -7
sound/soc/codecs/da7219-aad.c
··· 339 339 SND_JACK_HEADSET | SND_JACK_LINEOUT); 340 340 } 341 341 342 + static void da7219_aad_jack_det_work(struct work_struct *work) 343 + { 344 + struct da7219_aad_priv *da7219_aad = 345 + container_of(work, struct da7219_aad_priv, jack_det_work); 346 + struct snd_soc_component *component = da7219_aad->component; 347 + u8 srm_st; 348 + 349 + mutex_lock(&da7219_aad->jack_det_mutex); 350 + 351 + srm_st = snd_soc_component_read(component, DA7219_PLL_SRM_STS) & DA7219_PLL_SRM_STS_MCLK; 352 + msleep(da7219_aad->gnd_switch_delay * ((srm_st == 0x0) ? 2 : 1) - 4); 353 + /* Enable ground switch */ 354 + snd_soc_component_update_bits(component, 0xFB, 0x01, 0x01); 355 + 356 + mutex_unlock(&da7219_aad->jack_det_mutex); 357 + } 358 + 342 359 343 360 /* 344 361 * IRQ 345 362 */ 363 + 364 + static irqreturn_t da7219_aad_pre_irq_thread(int irq, void *data) 365 + { 366 + 367 + struct da7219_aad_priv *da7219_aad = data; 368 + 369 + if (!da7219_aad->jack_inserted) 370 + schedule_work(&da7219_aad->jack_det_work); 371 + 372 + return IRQ_WAKE_THREAD; 373 + } 346 374 347 375 static irqreturn_t da7219_aad_irq_thread(int irq, void *data) 348 376 { ··· 379 351 struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(component); 380 352 struct da7219_priv *da7219 = snd_soc_component_get_drvdata(component); 381 353 u8 events[DA7219_AAD_IRQ_REG_MAX]; 382 - u8 statusa, srm_st; 354 + u8 statusa; 383 355 int i, report = 0, mask = 0; 384 - 385 - srm_st = snd_soc_component_read(component, DA7219_PLL_SRM_STS) & DA7219_PLL_SRM_STS_MCLK; 386 - msleep(da7219_aad->gnd_switch_delay * ((srm_st == 0x0) ? 2 : 1) - 4); 387 - /* Enable ground switch */ 388 - snd_soc_component_update_bits(component, 0xFB, 0x01, 0x01); 389 356 390 357 /* Read current IRQ events */ 391 358 regmap_bulk_read(da7219->regmap, DA7219_ACCDET_IRQ_EVENT_A, ··· 399 376 dev_dbg(component->dev, "IRQ events = 0x%x|0x%x, status = 0x%x\n", 400 377 events[DA7219_AAD_IRQ_REG_A], events[DA7219_AAD_IRQ_REG_B], 401 378 statusa); 379 + 380 + if (!da7219_aad->jack_inserted) 381 + cancel_work_sync(&da7219_aad->jack_det_work); 402 382 403 383 if (statusa & DA7219_JACK_INSERTION_STS_MASK) { 404 384 /* Jack Insertion */ ··· 966 940 967 941 INIT_WORK(&da7219_aad->btn_det_work, da7219_aad_btn_det_work); 968 942 INIT_WORK(&da7219_aad->hptest_work, da7219_aad_hptest_work); 943 + INIT_WORK(&da7219_aad->jack_det_work, da7219_aad_jack_det_work); 969 944 970 - ret = request_threaded_irq(da7219_aad->irq, NULL, 945 + ret = request_threaded_irq(da7219_aad->irq, da7219_aad_pre_irq_thread, 971 946 da7219_aad_irq_thread, 972 947 IRQF_TRIGGER_LOW | IRQF_ONESHOT, 973 948 "da7219-aad", da7219_aad);
+4
sound/soc/codecs/da7219-aad.h
··· 11 11 #define __DA7219_AAD_H 12 12 13 13 #include <linux/timer.h> 14 + #include <linux/mutex.h> 14 15 #include <sound/soc.h> 15 16 #include <sound/jack.h> 16 17 #include <sound/da7219-aad.h> ··· 197 196 198 197 struct work_struct btn_det_work; 199 198 struct work_struct hptest_work; 199 + struct work_struct jack_det_work; 200 + 201 + struct mutex jack_det_mutex; 200 202 201 203 struct snd_soc_jack *jack; 202 204 bool micbias_resume_enable;
+5 -6
sound/soc/codecs/mt6358.c
··· 560 560 struct mt6358_priv *priv = snd_soc_component_get_drvdata(c); 561 561 int enabled = ucontrol->value.integer.value[0]; 562 562 563 + if (enabled < 0 || enabled > 1) 564 + return -EINVAL; 565 + 563 566 if (priv->wov_enabled != enabled) { 564 567 if (enabled) 565 568 mt6358_enable_wov_phase2(priv); ··· 570 567 mt6358_disable_wov_phase2(priv); 571 568 572 569 priv->wov_enabled = enabled; 570 + 571 + return 1; 573 572 } 574 573 575 574 return 0; ··· 637 632 "Audio Playback", 638 633 "Test Mode", 639 634 "HP Impedance", 640 - "undefined1", 641 - "undefined2", 642 - "undefined3", 643 635 }; 644 636 645 637 static int hp_in_mux_map_value[] = { ··· 645 643 HP_MUX_HP, 646 644 HP_MUX_TEST_MODE, 647 645 HP_MUX_HP_IMPEDANCE, 648 - HP_MUX_OPEN, 649 - HP_MUX_OPEN, 650 - HP_MUX_OPEN, 651 646 }; 652 647 653 648 static SOC_VALUE_ENUM_SINGLE_DECL(hpl_in_mux_map_enum,
+1 -1
sound/soc/codecs/sma1303.c
··· 569 569 ret += sma1303_regmap_update_bits(sma1303, 570 570 SMA1303_11_SYSTEM_CTRL2, 571 571 SMA1303_LR_DATA_SW_MASK, 572 - SMA1303_LR_DATA_SW_NORMAL, 572 + SMA1303_LR_DATA_SW_SWAP, 573 573 &temp); 574 574 if (temp == true) 575 575 change = true;
+23
sound/soc/intel/boards/sof_rt5682.c
··· 227 227 .callback = sof_rt5682_quirk_cb, 228 228 .matches = { 229 229 DMI_MATCH(DMI_PRODUCT_FAMILY, "Google_Rex"), 230 + DMI_MATCH(DMI_OEM_STRING, "AUDIO-MAX98360_ALC5682I_I2S"), 231 + }, 232 + .driver_data = (void *)(SOF_RT5682_MCLK_EN | 233 + SOF_RT5682_SSP_CODEC(2) | 234 + SOF_SPEAKER_AMP_PRESENT | 235 + SOF_MAX98360A_SPEAKER_AMP_PRESENT | 236 + SOF_RT5682_SSP_AMP(0) | 237 + SOF_RT5682_NUM_HDMIDEV(4) 238 + ), 239 + }, 240 + { 241 + .callback = sof_rt5682_quirk_cb, 242 + .matches = { 243 + DMI_MATCH(DMI_PRODUCT_FAMILY, "Google_Rex"), 230 244 }, 231 245 .driver_data = (void *)(SOF_RT5682_MCLK_EN | 232 246 SOF_RT5682_SSP_CODEC(2) | ··· 1116 1102 .driver_data = (kernel_ulong_t)(SOF_RT5682_MCLK_EN | 1117 1103 SOF_RT5682_SSP_CODEC(0) | 1118 1104 SOF_SPEAKER_AMP_PRESENT | 1105 + SOF_RT5682_SSP_AMP(1) | 1106 + SOF_RT5682_NUM_HDMIDEV(4)), 1107 + }, 1108 + { 1109 + .name = "mtl_mx98360_rt5682", 1110 + .driver_data = (kernel_ulong_t)(SOF_RT5682_MCLK_EN | 1111 + SOF_RT5682_SSP_CODEC(0) | 1112 + SOF_SPEAKER_AMP_PRESENT | 1113 + SOF_MAX98360A_SPEAKER_AMP_PRESENT | 1119 1114 SOF_RT5682_SSP_AMP(1) | 1120 1115 SOF_RT5682_NUM_HDMIDEV(4)), 1121 1116 },
+12
sound/soc/intel/common/soc-acpi-intel-mtl-match.c
··· 15 15 .codecs = {"MX98357A"} 16 16 }; 17 17 18 + static const struct snd_soc_acpi_codecs mtl_max98360a_amp = { 19 + .num_codecs = 1, 20 + .codecs = {"MX98360A"} 21 + }; 22 + 18 23 static const struct snd_soc_acpi_codecs mtl_rt5682_rt5682s_hp = { 19 24 .num_codecs = 2, 20 25 .codecs = {"10EC5682", "RTL5682"}, ··· 32 27 .machine_quirk = snd_soc_acpi_codec_list, 33 28 .quirk_data = &mtl_max98357a_amp, 34 29 .sof_tplg_filename = "sof-mtl-max98357a-rt5682.tplg", 30 + }, 31 + { 32 + .comp_ids = &mtl_rt5682_rt5682s_hp, 33 + .drv_name = "mtl_mx98360_rt5682", 34 + .machine_quirk = snd_soc_acpi_codec_list, 35 + .quirk_data = &mtl_max98360a_amp, 36 + .sof_tplg_filename = "sof-mtl-max98360a-rt5682.tplg", 35 37 }, 36 38 {}, 37 39 };
+3 -18
sound/soc/mediatek/mt8183/mt8183-dai-i2s.c
··· 141 141 struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt); 142 142 struct mtk_afe_i2s_priv *i2s_priv; 143 143 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 144 - int hd_en; 144 + int hd_en, change; 145 145 146 146 if (ucontrol->value.enumerated.item[0] >= e->items) 147 147 return -EINVAL; 148 148 149 149 hd_en = ucontrol->value.integer.value[0]; 150 - 151 - dev_info(afe->dev, "%s(), kcontrol name %s, hd_en %d\n", 152 - __func__, kcontrol->id.name, hd_en); 153 150 154 151 i2s_priv = get_i2s_priv_by_name(afe, kcontrol->id.name); 155 152 ··· 155 158 return -EINVAL; 156 159 } 157 160 161 + change = i2s_priv->low_jitter_en != hd_en; 158 162 i2s_priv->low_jitter_en = hd_en; 159 163 160 - return 0; 164 + return change; 161 165 } 162 166 163 167 static const struct snd_kcontrol_new mtk_dai_i2s_controls[] = { ··· 274 276 struct snd_soc_component *cmpnt = snd_soc_dapm_to_component(w->dapm); 275 277 struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt); 276 278 277 - dev_info(cmpnt->dev, "%s(), name %s, event 0x%x\n", 278 - __func__, w->name, event); 279 - 280 279 switch (event) { 281 280 case SND_SOC_DAPM_PRE_PMU: 282 281 if (strcmp(w->name, APLL1_W_NAME) == 0) ··· 301 306 struct snd_soc_component *cmpnt = snd_soc_dapm_to_component(w->dapm); 302 307 struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt); 303 308 struct mtk_afe_i2s_priv *i2s_priv; 304 - 305 - dev_info(cmpnt->dev, "%s(), name %s, event 0x%x\n", 306 - __func__, w->name, event); 307 309 308 310 i2s_priv = get_i2s_priv_by_name(afe, w->name); 309 311 ··· 707 715 unsigned int i2s_con = 0, fmt_con = I2S_FMT_I2S << I2S_FMT_SFT; 708 716 int ret = 0; 709 717 710 - dev_info(afe->dev, "%s(), id %d, rate %d, format %d\n", 711 - __func__, 712 - i2s_id, 713 - rate, format); 714 - 715 718 if (i2s_priv) { 716 719 i2s_priv->rate = rate; 717 720 ··· 796 809 dev_warn(afe->dev, "%s(), dir != SND_SOC_CLOCK_OUT", __func__); 797 810 return -EINVAL; 798 811 } 799 - 800 - dev_info(afe->dev, "%s(), freq %d\n", __func__, freq); 801 812 802 813 apll = mt8183_get_apll_by_rate(afe, freq); 803 814 apll_rate = mt8183_get_apll_rate(afe, apll);
+3 -8
sound/soc/mediatek/mt8188/mt8188-dai-etdm.c
··· 679 679 unsigned int old_val; 680 680 unsigned int mask; 681 681 unsigned int reg; 682 - unsigned int shift; 683 682 684 683 if (source >= e->items) 685 684 return -EINVAL; ··· 686 687 if (!strcmp(kcontrol->id.name, "ETDM_OUT1_Clock_Source")) { 687 688 reg = ETDM_OUT1_CON4; 688 689 mask = ETDM_OUT_CON4_CLOCK_MASK; 689 - shift = ETDM_OUT_CON4_CLOCK_SHIFT; 690 690 val = FIELD_PREP(ETDM_OUT_CON4_CLOCK_MASK, source); 691 691 } else if (!strcmp(kcontrol->id.name, "ETDM_OUT2_Clock_Source")) { 692 692 reg = ETDM_OUT2_CON4; 693 693 mask = ETDM_OUT_CON4_CLOCK_MASK; 694 - shift = ETDM_OUT_CON4_CLOCK_SHIFT; 695 694 val = FIELD_PREP(ETDM_OUT_CON4_CLOCK_MASK, source); 696 695 } else if (!strcmp(kcontrol->id.name, "ETDM_OUT3_Clock_Source")) { 697 696 reg = ETDM_OUT3_CON4; 698 697 mask = ETDM_OUT_CON4_CLOCK_MASK; 699 - shift = ETDM_OUT_CON4_CLOCK_SHIFT; 700 698 val = FIELD_PREP(ETDM_OUT_CON4_CLOCK_MASK, source); 701 699 } else if (!strcmp(kcontrol->id.name, "ETDM_IN1_Clock_Source")) { 702 700 reg = ETDM_IN1_CON2; 703 701 mask = ETDM_IN_CON2_CLOCK_MASK; 704 - shift = ETDM_IN_CON2_CLOCK_SHIFT; 705 702 val = FIELD_PREP(ETDM_IN_CON2_CLOCK_MASK, source); 706 703 } else if (!strcmp(kcontrol->id.name, "ETDM_IN2_Clock_Source")) { 707 704 reg = ETDM_IN2_CON2; 708 705 mask = ETDM_IN_CON2_CLOCK_MASK; 709 - shift = ETDM_IN_CON2_CLOCK_SHIFT; 710 706 val = FIELD_PREP(ETDM_IN_CON2_CLOCK_MASK, source); 711 707 } else { 712 708 return -EINVAL; ··· 709 715 710 716 regmap_read(afe->regmap, reg, &old_val); 711 717 old_val &= mask; 712 - old_val >>= shift; 713 - 714 718 if (old_val == val) 715 719 return 0; 716 720 ··· 2498 2506 2499 2507 /* etdm in only */ 2500 2508 for (i = 0; i < 2; i++) { 2509 + dai_id = ETDM_TO_DAI_ID(i); 2510 + etdm_data = afe_priv->dai_priv[dai_id]; 2511 + 2501 2512 snprintf(prop, sizeof(prop), "mediatek,%s-chn-disabled", 2502 2513 of_afe_etdms[i].name); 2503 2514
+19 -39
sound/soc/mediatek/mt8192/mt8192-dai-adda.c
··· 303 303 struct mt8192_afe_private *afe_priv = afe->platform_priv; 304 304 int mtkaif_dmic = afe_priv->mtkaif_dmic; 305 305 306 - dev_info(afe->dev, "%s(), name %s, event 0x%x, mtkaif_dmic %d\n", 307 - __func__, w->name, event, mtkaif_dmic); 308 - 309 306 switch (event) { 310 307 case SND_SOC_DAPM_PRE_PMU: 311 308 mt8192_afe_gpio_request(afe->dev, true, MT8192_DAI_ADDA, 1); ··· 341 344 struct mt8192_afe_private *afe_priv = afe->platform_priv; 342 345 int mtkaif_dmic = afe_priv->mtkaif_dmic_ch34; 343 346 int mtkaif_adda6_only = afe_priv->mtkaif_adda6_only; 344 - 345 - dev_info(afe->dev, 346 - "%s(), name %s, event 0x%x, mtkaif_dmic %d, mtkaif_adda6_only %d\n", 347 - __func__, w->name, event, mtkaif_dmic, mtkaif_adda6_only); 348 347 349 348 switch (event) { 350 349 case SND_SOC_DAPM_PRE_PMU: ··· 531 538 struct snd_soc_component *cmpnt = snd_soc_dapm_to_component(w->dapm); 532 539 struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt); 533 540 534 - dev_info(afe->dev, "%s(), name %s, event 0x%x\n", 535 - __func__, w->name, event); 536 - 537 541 switch (event) { 538 542 case SND_SOC_DAPM_PRE_PMU: 539 543 mt8192_afe_gpio_request(afe->dev, true, MT8192_DAI_ADDA, 0); ··· 553 563 { 554 564 struct snd_soc_component *cmpnt = snd_soc_dapm_to_component(w->dapm); 555 565 struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt); 556 - 557 - dev_info(afe->dev, "%s(), name %s, event 0x%x\n", 558 - __func__, w->name, event); 559 566 560 567 switch (event) { 561 568 case SND_SOC_DAPM_PRE_PMU: ··· 591 604 struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt); 592 605 struct mt8192_afe_private *afe_priv = afe->platform_priv; 593 606 int gain_db = ucontrol->value.integer.value[0]; 607 + bool change = false; 594 608 595 609 afe_priv->stf_positive_gain_db = gain_db; 596 610 597 611 if (gain_db >= 0 && gain_db <= 24) { 598 - regmap_update_bits(afe->regmap, 599 - AFE_SIDETONE_GAIN, 600 - POSITIVE_GAIN_MASK_SFT, 601 - (gain_db / 6) << POSITIVE_GAIN_SFT); 612 + regmap_update_bits_check(afe->regmap, 613 + AFE_SIDETONE_GAIN, 614 + POSITIVE_GAIN_MASK_SFT, 615 + (gain_db / 6) << POSITIVE_GAIN_SFT, 616 + &change); 602 617 } else { 603 - dev_warn(afe->dev, "%s(), gain_db %d invalid\n", 604 - __func__, gain_db); 618 + return -EINVAL; 605 619 } 606 - return 0; 620 + 621 + return change; 607 622 } 608 623 609 624 static int mt8192_adda_dmic_get(struct snd_kcontrol *kcontrol, ··· 626 637 struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt); 627 638 struct mt8192_afe_private *afe_priv = afe->platform_priv; 628 639 int dmic_on; 640 + bool change; 629 641 630 642 dmic_on = ucontrol->value.integer.value[0]; 631 643 632 - dev_info(afe->dev, "%s(), kcontrol name %s, dmic_on %d\n", 633 - __func__, kcontrol->id.name, dmic_on); 644 + change = (afe_priv->mtkaif_dmic != dmic_on) || 645 + (afe_priv->mtkaif_dmic_ch34 != dmic_on); 634 646 635 647 afe_priv->mtkaif_dmic = dmic_on; 636 648 afe_priv->mtkaif_dmic_ch34 = dmic_on; 637 - return 0; 649 + 650 + return change; 638 651 } 639 652 640 653 static int mt8192_adda6_only_get(struct snd_kcontrol *kcontrol, ··· 657 666 struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt); 658 667 struct mt8192_afe_private *afe_priv = afe->platform_priv; 659 668 int mtkaif_adda6_only; 669 + bool change; 660 670 661 671 mtkaif_adda6_only = ucontrol->value.integer.value[0]; 662 672 663 - dev_info(afe->dev, "%s(), kcontrol name %s, mtkaif_adda6_only %d\n", 664 - __func__, kcontrol->id.name, mtkaif_adda6_only); 665 - 673 + change = afe_priv->mtkaif_adda6_only != mtkaif_adda6_only; 666 674 afe_priv->mtkaif_adda6_only = mtkaif_adda6_only; 667 - return 0; 675 + 676 + return change; 668 677 } 669 678 670 679 static const struct snd_kcontrol_new mtk_adda_controls[] = { 671 680 SOC_SINGLE("Sidetone_Gain", AFE_SIDETONE_GAIN, 672 681 SIDE_TONE_GAIN_SFT, SIDE_TONE_GAIN_MASK, 0), 673 - SOC_SINGLE_EXT("Sidetone_Positive_Gain_dB", SND_SOC_NOPM, 0, 100, 0, 682 + SOC_SINGLE_EXT("Sidetone_Positive_Gain_dB", SND_SOC_NOPM, 0, 24, 0, 674 683 stf_positive_gain_get, stf_positive_gain_set), 675 684 SOC_SINGLE("ADDA_DL_GAIN", AFE_ADDA_DL_SRC2_CON1, 676 685 DL_2_GAIN_CTL_PRE_SFT, DL_2_GAIN_CTL_PRE_MASK, 0), ··· 740 749 } 741 750 742 751 regmap_read(afe->regmap, AFE_SIDETONE_CON1, &reg_value); 743 - 744 - dev_info(afe->dev, "%s(), name %s, event 0x%x, ul_rate 0x%x, AFE_SIDETONE_CON1 0x%x\n", 745 - __func__, w->name, event, ul_rate, reg_value); 746 752 747 753 switch (event) { 748 754 case SND_SOC_DAPM_PRE_PMU: ··· 1151 1163 unsigned int rate = params_rate(params); 1152 1164 int id = dai->id; 1153 1165 1154 - dev_info(afe->dev, "%s(), id %d, stream %d, rate %d\n", 1155 - __func__, 1156 - id, 1157 - substream->stream, 1158 - rate); 1159 - 1160 1166 if (substream->stream == SNDRV_PCM_STREAM_PLAYBACK) { 1161 1167 unsigned int dl_src2_con0 = 0; 1162 1168 unsigned int dl_src2_con1 = 0; ··· 1422 1440 { 1423 1441 struct mtk_base_afe_dai *dai; 1424 1442 struct mt8192_afe_private *afe_priv = afe->platform_priv; 1425 - 1426 - dev_info(afe->dev, "%s()\n", __func__); 1427 1443 1428 1444 dai = devm_kzalloc(afe->dev, sizeof(*dai), GFP_KERNEL); 1429 1445 if (!dai)
+3
sound/soc/mediatek/mt8195/mt8195-dai-etdm.c
··· 2567 2567 2568 2568 /* etdm in only */ 2569 2569 for (i = 0; i < 2; i++) { 2570 + dai_id = ETDM_TO_DAI_ID(i); 2571 + etdm_data = afe_priv->dai_priv[dai_id]; 2572 + 2570 2573 ret = snprintf(prop, sizeof(prop), 2571 2574 "mediatek,%s-chn-disabled", 2572 2575 of_afe_etdms[i].name);
+32 -32
sound/soc/sh/rcar/adg.c
··· 39 39 int clkin_size; 40 40 int clkout_size; 41 41 u32 ckr; 42 - u32 rbga; 43 - u32 rbgb; 42 + u32 brga; 43 + u32 brgb; 44 44 45 - int rbg_rate[ADG_HZ_SIZE]; /* RBGA / RBGB */ 45 + int brg_rate[ADG_HZ_SIZE]; /* BRGA / BRGB */ 46 46 }; 47 47 48 48 #define for_each_rsnd_clkin(pos, adg, i) \ ··· 75 75 [CLKOUT3] = "audio_clkout3", 76 76 }; 77 77 78 - static u32 rsnd_adg_calculate_rbgx(unsigned long div) 78 + static u32 rsnd_adg_calculate_brgx(unsigned long div) 79 79 { 80 80 int i; 81 81 ··· 131 131 adg->clkin_rate[CLKA], /* 0000: CLKA */ 132 132 adg->clkin_rate[CLKB], /* 0001: CLKB */ 133 133 adg->clkin_rate[CLKC], /* 0010: CLKC */ 134 - adg->rbg_rate[ADG_HZ_441], /* 0011: RBGA */ 135 - adg->rbg_rate[ADG_HZ_48], /* 0100: RBGB */ 134 + adg->brg_rate[ADG_HZ_441], /* 0011: BRGA */ 135 + adg->brg_rate[ADG_HZ_48], /* 0100: BRGB */ 136 136 }; 137 137 138 138 min = ~0; ··· 323 323 /* 324 324 * find divided clock from BRGA/BRGB 325 325 */ 326 - if (rate == adg->rbg_rate[ADG_HZ_441]) 326 + if (rate == adg->brg_rate[ADG_HZ_441]) 327 327 return 0x10; 328 328 329 - if (rate == adg->rbg_rate[ADG_HZ_48]) 329 + if (rate == adg->brg_rate[ADG_HZ_48]) 330 330 return 0x20; 331 331 332 332 return -EIO; ··· 358 358 ckr = 0x80000000; /* BRGB output = 48kHz */ 359 359 360 360 rsnd_mod_bset(adg_mod, BRGCKR, 0x80770000, adg->ckr | ckr); 361 - rsnd_mod_write(adg_mod, BRRA, adg->rbga); 362 - rsnd_mod_write(adg_mod, BRRB, adg->rbgb); 361 + rsnd_mod_write(adg_mod, BRRA, adg->brga); 362 + rsnd_mod_write(adg_mod, BRRB, adg->brgb); 363 363 364 364 dev_dbg(dev, "CLKOUT is based on BRG%c (= %dHz)\n", 365 365 (ckr) ? 'B' : 'A', 366 - (ckr) ? adg->rbg_rate[ADG_HZ_48] : 367 - adg->rbg_rate[ADG_HZ_441]); 366 + (ckr) ? adg->brg_rate[ADG_HZ_48] : 367 + adg->brg_rate[ADG_HZ_441]); 368 368 369 369 return 0; 370 370 } ··· 484 484 struct device *dev = rsnd_priv_to_dev(priv); 485 485 struct device_node *np = dev->of_node; 486 486 struct property *prop; 487 - u32 ckr, rbgx, rbga, rbgb; 487 + u32 ckr, brgx, brga, brgb; 488 488 u32 rate, div; 489 489 u32 req_rate[ADG_HZ_SIZE] = {}; 490 490 uint32_t count = 0; ··· 501 501 }; 502 502 503 503 ckr = 0; 504 - rbga = 2; /* default 1/6 */ 505 - rbgb = 2; /* default 1/6 */ 504 + brga = 2; /* default 1/6 */ 505 + brgb = 2; /* default 1/6 */ 506 506 507 507 /* 508 508 * ADG supports BRRA/BRRB output only ··· 543 543 if (0 == rate) /* not used */ 544 544 continue; 545 545 546 - /* RBGA */ 547 - if (!adg->rbg_rate[ADG_HZ_441] && (0 == rate % 44100)) { 546 + /* BRGA */ 547 + if (!adg->brg_rate[ADG_HZ_441] && (0 == rate % 44100)) { 548 548 div = 6; 549 549 if (req_Hz[ADG_HZ_441]) 550 550 div = rate / req_Hz[ADG_HZ_441]; 551 - rbgx = rsnd_adg_calculate_rbgx(div); 552 - if (BRRx_MASK(rbgx) == rbgx) { 553 - rbga = rbgx; 554 - adg->rbg_rate[ADG_HZ_441] = rate / div; 551 + brgx = rsnd_adg_calculate_brgx(div); 552 + if (BRRx_MASK(brgx) == brgx) { 553 + brga = brgx; 554 + adg->brg_rate[ADG_HZ_441] = rate / div; 555 555 ckr |= brg_table[i] << 20; 556 556 if (req_Hz[ADG_HZ_441]) 557 557 parent_clk_name = __clk_get_name(clk); 558 558 } 559 559 } 560 560 561 - /* RBGB */ 562 - if (!adg->rbg_rate[ADG_HZ_48] && (0 == rate % 48000)) { 561 + /* BRGB */ 562 + if (!adg->brg_rate[ADG_HZ_48] && (0 == rate % 48000)) { 563 563 div = 6; 564 564 if (req_Hz[ADG_HZ_48]) 565 565 div = rate / req_Hz[ADG_HZ_48]; 566 - rbgx = rsnd_adg_calculate_rbgx(div); 567 - if (BRRx_MASK(rbgx) == rbgx) { 568 - rbgb = rbgx; 569 - adg->rbg_rate[ADG_HZ_48] = rate / div; 566 + brgx = rsnd_adg_calculate_brgx(div); 567 + if (BRRx_MASK(brgx) == brgx) { 568 + brgb = brgx; 569 + adg->brg_rate[ADG_HZ_48] = rate / div; 570 570 ckr |= brg_table[i] << 16; 571 571 if (req_Hz[ADG_HZ_48]) 572 572 parent_clk_name = __clk_get_name(clk); ··· 620 620 621 621 rsnd_adg_get_clkout_end: 622 622 adg->ckr = ckr; 623 - adg->rbga = rbga; 624 - adg->rbgb = rbgb; 623 + adg->brga = brga; 624 + adg->brgb = brgb; 625 625 626 626 return 0; 627 627 ··· 663 663 __clk_get_name(clk), clk, clk_get_rate(clk)); 664 664 665 665 dbg_msg(dev, m, "BRGCKR = 0x%08x, BRRA/BRRB = 0x%x/0x%x\n", 666 - adg->ckr, adg->rbga, adg->rbgb); 667 - dbg_msg(dev, m, "BRGA (for 44100 base) = %d\n", adg->rbg_rate[ADG_HZ_441]); 668 - dbg_msg(dev, m, "BRGB (for 48000 base) = %d\n", adg->rbg_rate[ADG_HZ_48]); 666 + adg->ckr, adg->brga, adg->brgb); 667 + dbg_msg(dev, m, "BRGA (for 44100 base) = %d\n", adg->brg_rate[ADG_HZ_441]); 668 + dbg_msg(dev, m, "BRGB (for 48000 base) = %d\n", adg->brg_rate[ADG_HZ_48]); 669 669 670 670 /* 671 671 * Actual CLKOUT will be exchanged in rsnd_adg_ssi_clk_try_start()
+22 -5
sound/soc/soc-pcm.c
··· 1088 1088 static int soc_pcm_trigger(struct snd_pcm_substream *substream, int cmd) 1089 1089 { 1090 1090 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream); 1091 - int ret = -EINVAL, _ret = 0; 1091 + struct snd_soc_component *component; 1092 + int ret = -EINVAL, _ret = 0, start_dma_last = 0, i; 1092 1093 int rollback = 0; 1093 1094 1094 1095 switch (cmd) { 1095 1096 case SNDRV_PCM_TRIGGER_START: 1096 1097 case SNDRV_PCM_TRIGGER_RESUME: 1097 1098 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE: 1099 + /* Do we need to start dma last? */ 1100 + for_each_rtd_components(rtd, i, component) { 1101 + if (component->driver->start_dma_last) { 1102 + start_dma_last = 1; 1103 + break; 1104 + } 1105 + } 1106 + 1098 1107 ret = snd_soc_link_trigger(substream, cmd, 0); 1099 1108 if (ret < 0) 1100 1109 goto start_err; 1101 1110 1102 - ret = snd_soc_pcm_component_trigger(substream, cmd, 0); 1103 - if (ret < 0) 1104 - goto start_err; 1111 + if (start_dma_last) { 1112 + ret = snd_soc_pcm_dai_trigger(substream, cmd, 0); 1113 + if (ret < 0) 1114 + goto start_err; 1105 1115 1106 - ret = snd_soc_pcm_dai_trigger(substream, cmd, 0); 1116 + ret = snd_soc_pcm_component_trigger(substream, cmd, 0); 1117 + } else { 1118 + ret = snd_soc_pcm_component_trigger(substream, cmd, 0); 1119 + if (ret < 0) 1120 + goto start_err; 1121 + 1122 + ret = snd_soc_pcm_dai_trigger(substream, cmd, 0); 1123 + } 1107 1124 start_err: 1108 1125 if (ret < 0) 1109 1126 rollback = 1;