int asoc_simple_card_parse_card_name(struct snd_soc_card *card, char *prefix) { int ret; if (!prefix) prefix = ""; /* Parse the card name from DT */ ret = snd_soc_of_parse_card_name(card, "label"); if (ret < 0) { char prop[128]; snprintf(prop, sizeof(prop), "%sname", prefix); ret = snd_soc_of_parse_card_name(card, prop); if (ret < 0) return ret; } if (!card->name && card->dai_link) card->name = card->dai_link->name; dev_dbg(card->dev, "Card Name: %s\n", card->name ? card->name : ""); return 0; }
static int mop500_of_probe(struct platform_device *pdev, struct device_node *np) { struct device_node *codec_np, *msp_np[2]; int i; msp_np[0] = of_parse_phandle(np, "stericsson,cpu-dai", 0); msp_np[1] = of_parse_phandle(np, "stericsson,cpu-dai", 1); codec_np = of_parse_phandle(np, "stericsson,audio-codec", 0); if (!(msp_np[0] && msp_np[1] && codec_np)) { dev_err(&pdev->dev, "Phandle missing or invalid\n"); mop500_of_node_put(); return -EINVAL; } for (i = 0; i < 2; i++) { mop500_dai_links[i].cpu_of_node = msp_np[i]; mop500_dai_links[i].cpu_dai_name = NULL; mop500_dai_links[i].codec_of_node = codec_np; mop500_dai_links[i].codec_name = NULL; } snd_soc_of_parse_card_name(&mop500_card, "stericsson,card-name"); return 0; }
static int aml_m8_audio_probe(struct platform_device *pdev) { //struct device_node *np = pdev->dev.of_node; struct snd_soc_card *card = &aml_snd_soc_card; struct aml_audio_private_data *p_aml_audio; int ret = 0; printk(KERN_DEBUG "enter %s\n", __func__); #ifdef CONFIG_USE_OF p_aml_audio = devm_kzalloc(&pdev->dev, sizeof(struct aml_audio_private_data), GFP_KERNEL); if (!p_aml_audio) { dev_err(&pdev->dev, "Can't allocate aml_audio_private_data\n"); ret = -ENOMEM; goto err; } card->dev = &pdev->dev; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, p_aml_audio); if (!(pdev->dev.of_node)) { dev_err(&pdev->dev, "Must be instantiated using device tree\n"); ret = -EINVAL; goto err; } ret = snd_soc_of_parse_card_name(card, "aml,sound_card"); if (ret) goto err; ret = of_property_read_string_index(pdev->dev.of_node, "aml,codec_dai", 0, &aml_codec_dai_link[0].codec_dai_name); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "aml,audio-routing"); if (ret) goto err; // aml_codec_dai_link[0].codec_of_node = of_parse_phandle( // pdev->dev.of_node, "aml,audio-codec", 0); ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err; } aml_m8_pinmux_init(card); return 0; #endif err: kfree(p_aml_audio); return ret; }
static int imx_spdif_audio_probe(struct platform_device *pdev) { struct device_node *spdif_np, *np = pdev->dev.of_node; struct imx_spdif_data *data; int ret = 0; spdif_np = of_parse_phandle(np, "spdif-controller", 0); if (!spdif_np) { dev_err(&pdev->dev, "failed to find spdif-controller\n"); ret = -EINVAL; goto end; } data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); if (!data) { ret = -ENOMEM; goto end; } data->dai.name = "S/PDIF PCM"; data->dai.stream_name = "S/PDIF PCM"; data->dai.codec_dai_name = "snd-soc-dummy-dai"; data->dai.codec_name = "snd-soc-dummy"; data->dai.cpu_of_node = spdif_np; data->dai.platform_of_node = spdif_np; data->dai.playback_only = true; data->dai.capture_only = true; if (of_property_read_bool(np, "spdif-out")) data->dai.capture_only = false; if (of_property_read_bool(np, "spdif-in")) data->dai.playback_only = false; if (data->dai.playback_only && data->dai.capture_only) { dev_err(&pdev->dev, "no enabled S/PDIF DAI link\n"); goto end; } data->card.dev = &pdev->dev; data->card.dai_link = &data->dai; data->card.num_links = 1; data->card.owner = THIS_MODULE; ret = snd_soc_of_parse_card_name(&data->card, "model"); if (ret) goto end; ret = devm_snd_soc_register_card(&pdev->dev, &data->card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed: %d\n", ret); goto end; } end: of_node_put(spdif_np); return ret; }
static int odroidx2_audio_probe(struct platform_device *pdev) { struct device_node *snd_node = pdev->dev.of_node; struct snd_soc_card *card = &odroidx2; struct device_node *i2s_node, *codec_node; struct odroidx2_drv_data *dd; const struct of_device_id *of_id; int ret; of_id = of_match_node(odroidx2_audio_of_match, snd_node); dd = (struct odroidx2_drv_data *)of_id->data; card->num_dapm_widgets = dd->num_dapm_widgets; card->dapm_widgets = dd->dapm_widgets; card->dev = &pdev->dev; ret = snd_soc_of_parse_card_name(card, "samsung,model"); if (ret < 0) return ret; ret = snd_soc_of_parse_audio_routing(card, "samsung,audio-routing"); if (ret < 0) return ret; codec_node = of_parse_phandle(snd_node, "samsung,audio-codec", 0); if (!codec_node) { dev_err(&pdev->dev, "Failed parsing samsung,i2s-codec property\n"); return -EINVAL; } i2s_node = of_parse_phandle(snd_node, "samsung,i2s-controller", 0); if (!i2s_node) { dev_err(&pdev->dev, "Failed parsing samsung,i2s-controller property\n"); ret = -EINVAL; goto err_put_codec_n; } odroidx2_dai[0].codec_of_node = codec_node; odroidx2_dai[0].cpu_of_node = i2s_node; odroidx2_dai[0].platform_of_node = i2s_node; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card() failed: %d\n", ret); goto err_put_i2s_n; } return 0; err_put_i2s_n: of_node_put(i2s_node); err_put_codec_n: of_node_put(codec_node); return ret; }
static __devinit int msm8x10_asoc_machine_probe(struct platform_device *pdev) { struct snd_soc_card *card = &snd_soc_card_msm8x10; int ret; dev_dbg(&pdev->dev, "%s\n", __func__); if (!pdev->dev.of_node) { dev_err(&pdev->dev, "No platform supplied from device tree\n"); return -EINVAL; } card->dev = &pdev->dev; platform_set_drvdata(pdev, card); ret = snd_soc_of_parse_card_name(card, "qcom,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "qcom,audio-routing"); if (ret) goto err; mutex_init(&cdc_mclk_mutex); pcbcr = ioremap(MSM8X10_DINO_LPASS_DIGCODEC_CBCR, 4); if (!pcbcr) { ret = -ENOMEM; goto err1; } prcgr = ioremap(MSM8X10_DINO_LPASS_DIGCODEC_CMD_RCGR, 4); if (!prcgr) { ret = -ENOMEM; goto err1; } atomic_set(&mclk_rsc_ref, 0); mbhc_cfg.gpio_level_insert = of_property_read_bool(pdev->dev.of_node, "qcom,headset-jack-type-NC"); spdev = pdev; ret = snd_soc_register_card(card); if (ret == -EPROBE_DEFER) goto err1; else if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err1; } return 0; err1: mutex_destroy(&cdc_mclk_mutex); if (pcbcr) iounmap(pcbcr); if (prcgr) iounmap(prcgr); err: return ret; }
static int msm8x16_asoc_machine_probe(struct platform_device *pdev) { struct snd_soc_card *card; const char *card_dev_id = "qcom,msm-snd-card-id"; int ret, id; ret = of_property_read_u32(pdev->dev.of_node, card_dev_id, &id); if (ret) { dev_err(&pdev->dev, "%s: missing %s in dt node\n", __func__, card_dev_id); return ret; } pdev->id = id; dev_set_name(&pdev->dev, "%s.%d", "msm-snd-card", id); dev_dbg(&pdev->dev, "%s: dev name %s, id:%d\n", __func__, dev_name(&pdev->dev), pdev->id); dev_dbg(&pdev->dev, "%s-card:%d\n", __func__, pdev->id); if (!pdev->dev.of_node) { dev_err(&pdev->dev, "No platform supplied from device tree\n"); return -EINVAL; } if (pdev->id >= MAX_SND_CARDS) { dev_err(&pdev->dev, "Sound Card parsed is wrong\n"); return -EINVAL; } card = &bear_cards[pdev->id]; card->dev = &pdev->dev; platform_set_drvdata(pdev, card); ret = snd_soc_of_parse_card_name(card, "qcom,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "qcom,audio-routing"); if (ret) goto err; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err; } mutex_init(&cdc_mclk_mutex); atomic_set(&mclk_rsc_ref, 0); return 0; err: return ret; }
static int asoc_simple_card_parse_of(struct device_node *node, struct simple_card_data *priv) { struct device *dev = simple_priv_to_dev(priv); enum of_gpio_flags flags; u32 val; int ret; if (!node) return -EINVAL; /* Parse the card name from DT */ snd_soc_of_parse_card_name(&priv->snd_card, "simple-audio-card,name"); /* The off-codec widgets */ if (of_property_read_bool(node, "simple-audio-card,widgets")) { ret = snd_soc_of_parse_audio_simple_widgets(&priv->snd_card, "simple-audio-card,widgets"); if (ret) return ret; } /* DAPM routes */ if (of_property_read_bool(node, "simple-audio-card,routing")) { ret = snd_soc_of_parse_audio_routing(&priv->snd_card, "simple-audio-card,routing"); if (ret) return ret; } /* Factor to mclk, used in hw_params() */ ret = of_property_read_u32(node, "simple-audio-card,mclk-fs", &val); if (ret == 0) priv->mclk_fs = val; dev_dbg(dev, "New simple-card: %s\n", priv->snd_card.name ? priv->snd_card.name : ""); /* Single/Muti DAI link(s) & New style of DT node */ if (of_get_child_by_name(node, "simple-audio-card,dai-link")) { struct device_node *np = NULL; int i = 0; for_each_child_of_node(node, np) { dev_dbg(dev, "\tlink %d:\n", i); ret = asoc_simple_card_dai_link_of(np, priv, i, false); if (ret < 0) { of_node_put(np); return ret; } i++; } } else {
static int snd_rk_mc_probe(struct platform_device *pdev) { int ret = 0; struct snd_soc_card *card = &snd_soc_card_rk; struct device_node *np = pdev->dev.of_node; /* register the soc card */ card->dev = &pdev->dev; rk_dailink.codec_of_node = of_parse_phandle(np, "rockchip,audio-codec", 0); if (!rk_dailink.codec_of_node) { dev_err(&pdev->dev, "Property 'rockchip,audio-codec' missing or invalid\n"); return -EINVAL; } rk_dailink.cpu_of_node = of_parse_phandle(np, "rockchip,i2s-controller", 0); if (!rk_dailink.cpu_of_node) { dev_err(&pdev->dev, "Property 'rockchip,i2s-controller' missing or invalid\n"); return -EINVAL; } rk_dailink.platform_of_node = rk_dailink.cpu_of_node; rk_98090_headset_dev.codec_of_node = of_parse_phandle(np, "rockchip,headset-codec", 0); if (!rk_98090_headset_dev.codec_of_node) { dev_err(&pdev->dev, "Property 'rockchip,headset-codec' missing/invalid\n"); return -EINVAL; } ret = snd_soc_of_parse_card_name(card, "rockchip,model"); if (ret) { dev_err(&pdev->dev, "Soc parse card name failed %d\n", ret); return ret; } ret = devm_snd_soc_register_card(&pdev->dev, card); if (ret) { dev_err(&pdev->dev, "Soc register card failed %d\n", ret); return ret; } return ret; }
static int atmel_asoc_wm8904_dt_init(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct device_node *codec_np, *cpu_np; struct snd_soc_card *card = &atmel_asoc_wm8904_card; struct snd_soc_dai_link *dailink = &atmel_asoc_wm8904_dailink; int ret; if (!np) { dev_err(&pdev->dev, "only device tree supported\n"); return -EINVAL; } ret = snd_soc_of_parse_card_name(card, "atmel,model"); if (ret) { dev_err(&pdev->dev, "failed to parse card name\n"); return ret; } ret = snd_soc_of_parse_audio_routing(card, "atmel,audio-routing"); if (ret) { dev_err(&pdev->dev, "failed to parse audio routing\n"); return ret; } cpu_np = of_parse_phandle(np, "atmel,ssc-controller", 0); if (!cpu_np) { dev_err(&pdev->dev, "failed to get dai and pcm info\n"); ret = -EINVAL; return ret; } dailink->cpu_of_node = cpu_np; dailink->platform_of_node = cpu_np; of_node_put(cpu_np); codec_np = of_parse_phandle(np, "atmel,audio-codec", 0); if (!codec_np) { dev_err(&pdev->dev, "failed to get codec info\n"); ret = -EINVAL; return ret; } dailink->codec_of_node = codec_np; of_node_put(codec_np); return 0; }
static int tau_dac_probe(struct platform_device *pdev) { int ret; struct device_node *np; struct snd_soc_card_drvdata *drvdata; tau_dac_card.dev = &pdev->dev; drvdata = devm_kzalloc(&pdev->dev, sizeof(*drvdata), GFP_KERNEL); if (drvdata == NULL) return -ENOMEM; np = pdev->dev.of_node; if (np == NULL) { dev_err(&pdev->dev, "Device tree node not found\n"); return -ENODEV; } /* set dai */ ret = tau_dac_set_dai(np); if (ret != 0) { dev_err(&pdev->dev, "Setting dai failed: %d\n", ret); return ret; } /* set clocks */ ret = tau_dac_set_clk(&pdev->dev, drvdata); if (ret != 0) { if (ret != -EPROBE_DEFER) dev_err(&pdev->dev, "Getting clocks failed: %d\n", ret); return ret; } /* register card */ snd_soc_card_set_drvdata(&tau_dac_card, drvdata); snd_soc_of_parse_card_name(&tau_dac_card, "tau-dac,model"); ret = snd_soc_register_card(&tau_dac_card); if (ret != 0) { if (ret != -EPROBE_DEFER) dev_err(&pdev->dev, "snd_soc_register_card() failed: %d\n", ret); return ret; } return ret; }
int asoc_simple_card_parse_card_name(struct snd_soc_card *card, char *prefix) { char prop[128]; int ret; snprintf(prop, sizeof(prop), "%sname", prefix); /* Parse the card name from DT */ ret = snd_soc_of_parse_card_name(card, prop); if (ret < 0) return ret; if (!card->name && card->dai_link) card->name = card->dai_link->name; return 0; }
static int davinci_evm_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; const struct of_device_id *match = of_match_device(of_match_ptr(davinci_evm_dt_ids), &pdev->dev); struct snd_soc_dai_link *dai = (struct snd_soc_dai_link *) match->data; struct snd_soc_card_drvdata_davinci *drvdata = NULL; int ret = 0; evm_soc_card.dai_link = dai; dai->codec_of_node = of_parse_phandle(np, "ti,audio-codec", 0); if (!dai->codec_of_node) return -EINVAL; dai->cpu_of_node = of_parse_phandle(np, "ti,mcasp-controller", 0); if (!dai->cpu_of_node) return -EINVAL; dai->platform_of_node = dai->cpu_of_node; evm_soc_card.dev = &pdev->dev; ret = snd_soc_of_parse_card_name(&evm_soc_card, "ti,model"); if (ret) return ret; drvdata = devm_kzalloc(&pdev->dev, sizeof(*drvdata), GFP_KERNEL); if (!drvdata) return -ENOMEM; ret = of_property_read_u32(np, "ti,codec-clock-rate", &drvdata->sysclk); if (ret < 0) return -EINVAL; snd_soc_card_set_drvdata(&evm_soc_card, drvdata); ret = devm_snd_soc_register_card(&pdev->dev, &evm_soc_card); if (ret) dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); return ret; }
static int snow_probe(struct platform_device *pdev) { struct snd_soc_card *card = &snow_snd; struct device_node *i2s_node, *codec_node; int i, ret; i2s_node = of_parse_phandle(pdev->dev.of_node, "samsung,i2s-controller", 0); if (!i2s_node) { dev_err(&pdev->dev, "Property 'i2s-controller' missing or invalid\n"); return -EINVAL; } codec_node = of_parse_phandle(pdev->dev.of_node, "samsung,audio-codec", 0); if (!codec_node) { dev_err(&pdev->dev, "Property 'audio-codec' missing or invalid\n"); return -EINVAL; } for (i = 0; i < ARRAY_SIZE(snow_dai); i++) { snow_dai[i].codec_of_node = codec_node; snow_dai[i].cpu_of_node = i2s_node; snow_dai[i].platform_of_node = i2s_node; } card->dev = &pdev->dev; /* Update card-name if provided through DT, else use default name */ snd_soc_of_parse_card_name(card, "samsung,model"); ret = devm_snd_soc_register_card(&pdev->dev, card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); return ret; } return ret; }
static int tegra_alc5632_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct snd_soc_card *card = &snd_soc_tegra_alc5632; struct tegra_alc5632 *alc5632; int ret; alc5632 = devm_kzalloc(&pdev->dev, sizeof(struct tegra_alc5632), GFP_KERNEL); if (!alc5632) { dev_err(&pdev->dev, "Can't allocate tegra_alc5632\n"); return -ENOMEM; } card->dev = &pdev->dev; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, alc5632); alc5632->gpio_hp_det = of_get_named_gpio(np, "nvidia,hp-det-gpios", 0); if (alc5632->gpio_hp_det == -EPROBE_DEFER) return -EPROBE_DEFER; ret = snd_soc_of_parse_card_name(card, "nvidia,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "nvidia,audio-routing"); if (ret) goto err; tegra_alc5632_dai.codec_of_node = of_parse_phandle( pdev->dev.of_node, "nvidia,audio-codec", 0); if (!tegra_alc5632_dai.codec_of_node) { dev_err(&pdev->dev, "Property 'nvidia,audio-codec' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_alc5632_dai.cpu_of_node = of_parse_phandle(np, "nvidia,i2s-controller", 0); if (!tegra_alc5632_dai.cpu_of_node) { dev_err(&pdev->dev, "Property 'nvidia,i2s-controller' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_alc5632_dai.platform_of_node = tegra_alc5632_dai.cpu_of_node; ret = tegra_asoc_utils_init(&alc5632->util_data, &pdev->dev); if (ret) goto err; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err_fini_utils; } return 0; err_fini_utils: tegra_asoc_utils_fini(&alc5632->util_data); err: return ret; }
static int eukrea_tlv320_probe(struct platform_device *pdev) { int ret; int int_port = 0, ext_port; struct device_node *np = pdev->dev.of_node; struct device_node *ssi_np = NULL, *codec_np = NULL; eukrea_tlv320.dev = &pdev->dev; if (np) { ret = snd_soc_of_parse_card_name(&eukrea_tlv320, "eukrea,model"); if (ret) { dev_err(&pdev->dev, "eukrea,model node missing or invalid.\n"); goto err; } ssi_np = of_parse_phandle(pdev->dev.of_node, "ssi-controller", 0); if (!ssi_np) { dev_err(&pdev->dev, "ssi-controller missing or invalid.\n"); ret = -ENODEV; goto err; } codec_np = of_parse_phandle(ssi_np, "codec-handle", 0); if (codec_np) eukrea_tlv320_dai.codec_of_node = codec_np; else dev_err(&pdev->dev, "codec-handle node missing or invalid.\n"); ret = of_property_read_u32(np, "fsl,mux-int-port", &int_port); if (ret) { dev_err(&pdev->dev, "fsl,mux-int-port node missing or invalid.\n"); return ret; } ret = of_property_read_u32(np, "fsl,mux-ext-port", &ext_port); if (ret) { dev_err(&pdev->dev, "fsl,mux-ext-port node missing or invalid.\n"); return ret; } /* * The port numbering in the hardware manual starts at 1, while * the audmux API expects it starts at 0. */ int_port--; ext_port--; eukrea_tlv320_dai.cpu_of_node = ssi_np; eukrea_tlv320_dai.platform_of_node = ssi_np; } else { eukrea_tlv320_dai.cpu_dai_name = "imx-ssi.0"; eukrea_tlv320_dai.platform_name = "imx-ssi.0"; eukrea_tlv320_dai.codec_name = "tlv320aic23-codec.0-001a"; eukrea_tlv320.name = "cpuimx-audio"; } if (machine_is_eukrea_cpuimx27() || of_find_compatible_node(NULL, NULL, "fsl,imx21-audmux")) { imx_audmux_v1_configure_port(MX27_AUDMUX_HPCR1_SSI0, IMX_AUDMUX_V1_PCR_SYN | IMX_AUDMUX_V1_PCR_TFSDIR | IMX_AUDMUX_V1_PCR_TCLKDIR | IMX_AUDMUX_V1_PCR_RFSDIR | IMX_AUDMUX_V1_PCR_RCLKDIR | IMX_AUDMUX_V1_PCR_TFCSEL(MX27_AUDMUX_HPCR3_SSI_PINS_4) | IMX_AUDMUX_V1_PCR_RFCSEL(MX27_AUDMUX_HPCR3_SSI_PINS_4) | IMX_AUDMUX_V1_PCR_RXDSEL(MX27_AUDMUX_HPCR3_SSI_PINS_4) ); imx_audmux_v1_configure_port(MX27_AUDMUX_HPCR3_SSI_PINS_4, IMX_AUDMUX_V1_PCR_SYN | IMX_AUDMUX_V1_PCR_RXDSEL(MX27_AUDMUX_HPCR1_SSI0) ); } else if (machine_is_eukrea_cpuimx25sd() || machine_is_eukrea_cpuimx35sd() || machine_is_eukrea_cpuimx51sd() || of_find_compatible_node(NULL, NULL, "fsl,imx31-audmux")) { if (!np) ext_port = machine_is_eukrea_cpuimx25sd() ? 4 : 3; imx_audmux_v2_configure_port(int_port, IMX_AUDMUX_V2_PTCR_SYN | IMX_AUDMUX_V2_PTCR_TFSDIR | IMX_AUDMUX_V2_PTCR_TFSEL(ext_port) | IMX_AUDMUX_V2_PTCR_TCLKDIR | IMX_AUDMUX_V2_PTCR_TCSEL(ext_port), IMX_AUDMUX_V2_PDCR_RXDSEL(ext_port) ); imx_audmux_v2_configure_port(ext_port, IMX_AUDMUX_V2_PTCR_SYN, IMX_AUDMUX_V2_PDCR_RXDSEL(int_port) ); } else { if (np) { /* The eukrea,asoc-tlv320 driver was explicitely * requested (through the device tree). */ dev_err(&pdev->dev, "Missing or invalid audmux DT node.\n"); return -ENODEV; } else { /* Return happy. * We might run on a totally different machine. */ return 0; } } ret = snd_soc_register_card(&eukrea_tlv320); err: if (ret) dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); of_node_put(ssi_np); return ret; }
static int omap_twl4030_probe(struct platform_device *pdev) { struct omap_tw4030_pdata *pdata = dev_get_platdata(&pdev->dev); struct device_node *node = pdev->dev.of_node; struct snd_soc_card *card = &omap_twl4030_card; struct omap_twl4030 *priv; int ret = 0; card->dev = &pdev->dev; priv = devm_kzalloc(&pdev->dev, sizeof(struct omap_twl4030), GFP_KERNEL); if (priv == NULL) return -ENOMEM; if (node) { struct device_node *dai_node; struct property *prop; if (snd_soc_of_parse_card_name(card, "ti,model")) { dev_err(&pdev->dev, "Card name is not provided\n"); return -ENODEV; } dai_node = of_parse_phandle(node, "ti,mcbsp", 0); if (!dai_node) { dev_err(&pdev->dev, "McBSP node is not provided\n"); return -EINVAL; } omap_twl4030_dai_links[0].cpu_dai_name = NULL; omap_twl4030_dai_links[0].cpu_of_node = dai_node; dai_node = of_parse_phandle(node, "ti,mcbsp-voice", 0); if (!dai_node) { card->num_links = 1; } else { omap_twl4030_dai_links[1].cpu_dai_name = NULL; omap_twl4030_dai_links[1].cpu_of_node = dai_node; } priv->jack_detect = of_get_named_gpio(node, "ti,jack-det-gpio", 0); /* Optional: audio routing can be provided */ prop = of_find_property(node, "ti,audio-routing", NULL); if (prop) { ret = snd_soc_of_parse_audio_routing(card, "ti,audio-routing"); if (ret) return ret; card->fully_routed = 1; } } else if (pdata) { if (pdata->card_name) { card->name = pdata->card_name; } else { dev_err(&pdev->dev, "Card name is not provided\n"); return -ENODEV; } if (!pdata->voice_connected) card->num_links = 1; priv->jack_detect = pdata->jack_detect; } else { dev_err(&pdev->dev, "Missing pdata\n"); return -ENODEV; } snd_soc_card_set_drvdata(card, priv); ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card() failed: %d\n", ret); return ret; } return 0; }
static int at91sam9g20ek_audio_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct device_node *codec_np, *cpu_np; struct clk *pllb; struct snd_soc_card *card = &snd_soc_at91sam9g20ek; int ret; if (!np) { return -ENODEV; } ret = atmel_ssc_set_audio(0); if (ret) { dev_err(&pdev->dev, "ssc channel is not valid\n"); return -EINVAL; } /* * Codec MCLK is supplied by PCK0 - set it up. */ mclk = clk_get(NULL, "pck0"); if (IS_ERR(mclk)) { printk(KERN_ERR "ASoC: Failed to get MCLK\n"); ret = PTR_ERR(mclk); goto err; } pllb = clk_get(NULL, "pllb"); if (IS_ERR(pllb)) { printk(KERN_ERR "ASoC: Failed to get PLLB\n"); ret = PTR_ERR(pllb); goto err_mclk; } ret = clk_set_parent(mclk, pllb); clk_put(pllb); if (ret != 0) { printk(KERN_ERR "ASoC: Failed to set MCLK parent\n"); goto err_mclk; } clk_set_rate(mclk, MCLK_RATE); card->dev = &pdev->dev; /* Parse device node info */ ret = snd_soc_of_parse_card_name(card, "atmel,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "atmel,audio-routing"); if (ret) goto err; /* Parse codec info */ at91sam9g20ek_dai.codec_name = NULL; codec_np = of_parse_phandle(np, "atmel,audio-codec", 0); if (!codec_np) { dev_err(&pdev->dev, "codec info missing\n"); return -EINVAL; } at91sam9g20ek_dai.codec_of_node = codec_np; /* Parse dai and platform info */ at91sam9g20ek_dai.cpu_dai_name = NULL; at91sam9g20ek_dai.platform_name = NULL; cpu_np = of_parse_phandle(np, "atmel,ssc-controller", 0); if (!cpu_np) { dev_err(&pdev->dev, "dai and pcm info missing\n"); return -EINVAL; } at91sam9g20ek_dai.cpu_of_node = cpu_np; at91sam9g20ek_dai.platform_of_node = cpu_np; of_node_put(codec_np); of_node_put(cpu_np); ret = snd_soc_register_card(card); if (ret) { printk(KERN_ERR "ASoC: snd_soc_register_card() failed\n"); } return ret; err_mclk: clk_put(mclk); mclk = NULL; err: atmel_ssc_put_audio(0); return ret; }
static int sam9x5_wm8731_driver_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct device_node *codec_np, *cpu_np; struct snd_soc_card *card; struct snd_soc_dai_link *dai; struct sam9x5_drvdata *priv; int ret; if (!np) { dev_err(&pdev->dev, "No device node supplied\n"); return -EINVAL; } card = devm_kzalloc(&pdev->dev, sizeof(*card), GFP_KERNEL); priv = devm_kzalloc(&pdev->dev, sizeof(*priv), GFP_KERNEL); dai = devm_kzalloc(&pdev->dev, sizeof(*dai), GFP_KERNEL); if (!dai || !card || !priv) { ret = -ENOMEM; goto out; } snd_soc_card_set_drvdata(card, priv); card->dev = &pdev->dev; card->owner = THIS_MODULE; card->dai_link = dai; card->num_links = 1; card->dapm_widgets = sam9x5_dapm_widgets; card->num_dapm_widgets = ARRAY_SIZE(sam9x5_dapm_widgets); dai->name = "WM8731"; dai->stream_name = "WM8731 PCM"; dai->codec_dai_name = "wm8731-hifi"; dai->init = sam9x5_wm8731_init; dai->dai_fmt = SND_SOC_DAIFMT_DSP_A | SND_SOC_DAIFMT_NB_NF | SND_SOC_DAIFMT_CBM_CFM; ret = snd_soc_of_parse_card_name(card, "atmel,model"); if (ret) { dev_err(&pdev->dev, "atmel,model node missing\n"); goto out; } ret = snd_soc_of_parse_audio_routing(card, "atmel,audio-routing"); if (ret) { dev_err(&pdev->dev, "atmel,audio-routing node missing\n"); goto out; } codec_np = of_parse_phandle(np, "atmel,audio-codec", 0); if (!codec_np) { dev_err(&pdev->dev, "atmel,audio-codec node missing\n"); ret = -EINVAL; goto out; } dai->codec_of_node = codec_np; cpu_np = of_parse_phandle(np, "atmel,ssc-controller", 0); if (!cpu_np) { dev_err(&pdev->dev, "atmel,ssc-controller node missing\n"); ret = -EINVAL; goto out; } dai->cpu_of_node = cpu_np; dai->platform_of_node = cpu_np; priv->ssc_id = of_alias_get_id(cpu_np, "ssc"); ret = atmel_ssc_set_audio(priv->ssc_id); if (ret != 0) { dev_err(&pdev->dev, "Failed to set SSC %d for audio: %d\n", ret, priv->ssc_id); goto out; } of_node_put(codec_np); of_node_put(cpu_np); ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "Platform device allocation failed\n"); goto out_put_audio; } dev_dbg(&pdev->dev, "%s ok\n", __func__); return ret; out_put_audio: atmel_ssc_put_audio(priv->ssc_id); out: return ret; }
static int tegra_wm8753_driver_probe(struct platform_device *pdev) { struct snd_soc_card *card = &snd_soc_tegra_wm8753; struct tegra_wm8753 *machine; struct tegra_asoc_platform_data *pdata; int ret; pdata = pdev->dev.platform_data; if (!pdata) { dev_err(&pdev->dev, "No platform data supplied\n"); return -EINVAL; } machine = devm_kzalloc(&pdev->dev, sizeof(struct tegra_wm8753), GFP_KERNEL); if (!machine) { dev_err(&pdev->dev, "Can't allocate tegra_wm8753 struct\n"); ret = -ENOMEM; goto err; } card->dev = &pdev->dev; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, machine); ret = snd_soc_of_parse_card_name(card, "nvidia,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "nvidia,audio-routing"); if (ret) goto err; tegra_wm8753_dai.codec_of_node = of_parse_phandle( pdev->dev.of_node, "nvidia,audio-codec", 0); if (!tegra_wm8753_dai.codec_of_node) { dev_err(&pdev->dev, "Property 'nvidia,audio-codec' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_wm8753_dai.cpu_of_node = of_parse_phandle( pdev->dev.of_node, "nvidia,i2s-controller", 0); if (!tegra_wm8753_dai.cpu_of_node) { dev_err(&pdev->dev, "Property 'nvidia,i2s-controller' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_wm8753_dai.platform_of_node = tegra_wm8753_dai.cpu_of_node; ret = tegra_asoc_utils_init(&machine->util_data, &pdev->dev, card); if (ret) goto err; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err_fini_utils; } if (!card->instantiated) { dev_err(&pdev->dev, "No WM8753 codec\n"); goto err_unregister_card; } #ifdef CONFIG_SWITCH /* Add h2w swith class support */ ret = tegra_asoc_switch_register(&wired_switch_dev); if (ret < 0) { dev_err(&pdev->dev, "not able to register switch device\n"); goto err_unregister_card; } #endif #ifndef CONFIG_ARCH_TEGRA_2x_SOC ret = tegra_asoc_utils_set_parent(&machine->util_data, pdata->i2s_param[HIFI_CODEC].is_i2s_master); if (ret) { dev_err(&pdev->dev, "tegra_asoc_utils_set_parent failed (%d)\n", ret); goto err_unregister_card; } #endif return 0; err_unregister_card: snd_soc_unregister_card(card); err_fini_utils: tegra_asoc_utils_fini(&machine->util_data); err: return ret; }
static int tegra_wm9712_driver_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct snd_soc_card *card = &snd_soc_tegra_wm9712; struct tegra_wm9712 *machine; int ret; machine = devm_kzalloc(&pdev->dev, sizeof(struct tegra_wm9712), GFP_KERNEL); if (!machine) { dev_err(&pdev->dev, "Can't allocate tegra_wm9712 struct\n"); return -ENOMEM; } card->dev = &pdev->dev; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, machine); machine->codec = platform_device_alloc("wm9712-codec", -1); if (!machine->codec) { dev_err(&pdev->dev, "Can't allocate wm9712 platform device\n"); return -ENOMEM; } ret = platform_device_add(machine->codec); if (ret) goto codec_put; ret = snd_soc_of_parse_card_name(card, "nvidia,model"); if (ret) goto codec_unregister; ret = snd_soc_of_parse_audio_routing(card, "nvidia,audio-routing"); if (ret) goto codec_unregister; tegra_wm9712_dai.cpu_of_node = of_parse_phandle(np, "nvidia,ac97-controller", 0); if (!tegra_wm9712_dai.cpu_of_node) { dev_err(&pdev->dev, "Property 'nvidia,ac97-controller' missing or invalid\n"); ret = -EINVAL; goto codec_unregister; } tegra_wm9712_dai.platform_of_node = tegra_wm9712_dai.cpu_of_node; ret = tegra_asoc_utils_init(&machine->util_data, &pdev->dev); if (ret) goto codec_unregister; ret = tegra_asoc_utils_set_ac97_rate(&machine->util_data); if (ret) goto asoc_utils_fini; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto asoc_utils_fini; } return 0; asoc_utils_fini: tegra_asoc_utils_fini(&machine->util_data); codec_unregister: platform_device_del(machine->codec); codec_put: platform_device_put(machine->codec); return ret; }
static int omap_abe_probe(struct platform_device *pdev) { struct omap_abe_twl6040_data *pdata = dev_get_platdata(&pdev->dev); struct device_node *node = pdev->dev.of_node; struct snd_soc_card *card = &omap_abe_card; struct abe_twl6040 *priv; int num_links = 0; int ret = 0; card->dev = &pdev->dev; priv = devm_kzalloc(&pdev->dev, sizeof(struct abe_twl6040), GFP_KERNEL); if (priv == NULL) return -ENOMEM; priv->dmic_codec_dev = ERR_PTR(-EINVAL); if (node) { struct device_node *dai_node; if (snd_soc_of_parse_card_name(card, "ti,model")) { dev_err(&pdev->dev, "Card name is not provided\n"); return -ENODEV; } ret = snd_soc_of_parse_audio_routing(card, "ti,audio-routing"); if (ret) { dev_err(&pdev->dev, "Error while parsing DAPM routing\n"); return ret; } dai_node = of_parse_phandle(node, "ti,mcpdm", 0); if (!dai_node) { dev_err(&pdev->dev, "McPDM node is not provided\n"); return -EINVAL; } abe_twl6040_dai_links[0].cpu_dai_name = NULL; abe_twl6040_dai_links[0].cpu_of_node = dai_node; dai_node = of_parse_phandle(node, "ti,dmic", 0); if (dai_node) { num_links = 2; abe_twl6040_dai_links[1].cpu_dai_name = NULL; abe_twl6040_dai_links[1].cpu_of_node = dai_node; priv->dmic_codec_dev = platform_device_register_simple( "dmic-codec", -1, NULL, 0); if (IS_ERR(priv->dmic_codec_dev)) { dev_err(&pdev->dev, "Can't instantiate dmic-codec\n"); return PTR_ERR(priv->dmic_codec_dev); } } else { num_links = 1; } priv->jack_detection = of_property_read_bool(node, "ti,jack-detection"); of_property_read_u32(node, "ti,mclk-freq", &priv->mclk_freq); if (!priv->mclk_freq) { dev_err(&pdev->dev, "MCLK frequency not provided\n"); ret = -EINVAL; goto err_unregister; } omap_abe_card.fully_routed = 1; } else if (pdata) { if (pdata->card_name) { card->name = pdata->card_name; } else { dev_err(&pdev->dev, "Card name is not provided\n"); return -ENODEV; } if (pdata->has_dmic) num_links = 2; else num_links = 1; priv->jack_detection = pdata->jack_detection; priv->mclk_freq = pdata->mclk_freq; } else { dev_err(&pdev->dev, "Missing pdata\n"); return -ENODEV; } if (!priv->mclk_freq) { dev_err(&pdev->dev, "MCLK frequency missing\n"); ret = -ENODEV; goto err_unregister; } card->dai_link = abe_twl6040_dai_links; card->num_links = num_links; snd_soc_card_set_drvdata(card, priv); ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card() failed: %d\n", ret); goto err_unregister; } return 0; err_unregister: if (!IS_ERR(priv->dmic_codec_dev)) platform_device_unregister(priv->dmic_codec_dev); return ret; }
static int tegra_rt5677_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct snd_soc_card *card = &snd_soc_tegra_rt5677; struct tegra_rt5677 *machine; int ret; machine = devm_kzalloc(&pdev->dev, sizeof(struct tegra_rt5677), GFP_KERNEL); if (!machine) return -ENOMEM; card->dev = &pdev->dev; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, machine); machine->gpio_hp_det = of_get_named_gpio(np, "nvidia,hp-det-gpios", 0); if (machine->gpio_hp_det == -EPROBE_DEFER) return -EPROBE_DEFER; machine->gpio_mic_present = of_get_named_gpio(np, "nvidia,mic-present-gpios", 0); if (machine->gpio_mic_present == -EPROBE_DEFER) return -EPROBE_DEFER; machine->gpio_hp_en = of_get_named_gpio(np, "nvidia,hp-en-gpios", 0); if (machine->gpio_hp_en == -EPROBE_DEFER) return -EPROBE_DEFER; if (gpio_is_valid(machine->gpio_hp_en)) { ret = devm_gpio_request_one(&pdev->dev, machine->gpio_hp_en, GPIOF_OUT_INIT_LOW, "hp_en"); if (ret) { dev_err(card->dev, "cannot get hp_en gpio\n"); return ret; } } machine->gpio_dmic_clk_en = of_get_named_gpio(np, "nvidia,dmic-clk-en-gpios", 0); if (machine->gpio_dmic_clk_en == -EPROBE_DEFER) return -EPROBE_DEFER; if (gpio_is_valid(machine->gpio_dmic_clk_en)) { ret = devm_gpio_request_one(&pdev->dev, machine->gpio_dmic_clk_en, GPIOF_OUT_INIT_HIGH, "dmic_clk_en"); if (ret) { dev_err(card->dev, "cannot get dmic_clk_en gpio\n"); return ret; } } ret = snd_soc_of_parse_card_name(card, "nvidia,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "nvidia,audio-routing"); if (ret) goto err; tegra_rt5677_dai.codec_of_node = of_parse_phandle(np, "nvidia,audio-codec", 0); if (!tegra_rt5677_dai.codec_of_node) { dev_err(&pdev->dev, "Property 'nvidia,audio-codec' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_rt5677_dai.cpu_of_node = of_parse_phandle(np, "nvidia,i2s-controller", 0); if (!tegra_rt5677_dai.cpu_of_node) { dev_err(&pdev->dev, "Property 'nvidia,i2s-controller' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_rt5677_dai.platform_of_node = tegra_rt5677_dai.cpu_of_node; ret = tegra_asoc_utils_init(&machine->util_data, &pdev->dev); if (ret) goto err; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err_fini_utils; } return 0; err_fini_utils: tegra_asoc_utils_fini(&machine->util_data); err: return ret; }
static __devinit int msm8226_asoc_machine_probe(struct platform_device *pdev) { struct snd_soc_card *card = &snd_soc_card_msm8226; struct msm8226_asoc_mach_data *pdata; int ret; const char *auxpcm_pri_gpio_set = NULL; if (!pdev->dev.of_node) { dev_err(&pdev->dev, "No platform supplied from device tree\n"); return -EINVAL; } pdata = devm_kzalloc(&pdev->dev, sizeof(struct msm8226_asoc_mach_data), GFP_KERNEL); if (!pdata) { dev_err(&pdev->dev, "Can't allocate msm8226_asoc_mach_data\n"); ret = -ENOMEM; goto err; } /* Parse AUXPCM info from DT */ ret = msm8226_dtparse_auxpcm(pdev, &pdata->auxpcm_ctrl, msm_auxpcm_gpio_name); if (ret) { dev_err(&pdev->dev, "%s: Auxpcm pin data parse failed\n", __func__); goto err; } card->dev = &pdev->dev; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, pdata); ret = snd_soc_of_parse_card_name(card, "qcom,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "qcom,audio-routing"); if (ret) goto err; ret = of_property_read_u32(pdev->dev.of_node, "qcom,tapan-mclk-clk-freq", &pdata->mclk_freq); if (ret) { dev_err(&pdev->dev, "Looking up %s property in node %s failed", "qcom,tapan-mclk-clk-freq", pdev->dev.of_node->full_name); goto err; } if (pdata->mclk_freq != 9600000) { dev_err(&pdev->dev, "unsupported tapan mclk freq %u\n", pdata->mclk_freq); ret = -EINVAL; goto err; } pdata->mclk_gpio = of_get_named_gpio(pdev->dev.of_node, "qcom,cdc-mclk-gpios", 0); if (pdata->mclk_gpio < 0) { dev_err(&pdev->dev, "Looking up %s property in node %s failed %d\n", "qcom, cdc-mclk-gpios", pdev->dev.of_node->full_name, pdata->mclk_gpio); ret = -ENODEV; goto err; } vdd_spkr_gpio = of_get_named_gpio(pdev->dev.of_node, "qcom,cdc-vdd-spkr-gpios", 0); if (vdd_spkr_gpio < 0) { dev_err(&pdev->dev, "Looking up %s property in node %s failed %d\n", "qcom, cdc-vdd-spkr-gpios", pdev->dev.of_node->full_name, vdd_spkr_gpio); } else { ret = gpio_request(vdd_spkr_gpio, "TAPAN_CODEC_VDD_SPKR"); if (ret) { /* GPIO to enable EXT VDD exists, but failed request */ dev_err(card->dev, "%s: Failed to request tapan vdd spkr gpio %d\n", __func__, vdd_spkr_gpio); goto err; } } mbhc_cfg.gpio_level_insert = of_property_read_bool(pdev->dev.of_node, "qcom,headset-jack-type-NO"); msm8226_setup_hs_jack(pdev, pdata); ret = msm8226_prepare_codec_mclk(card); if (ret) goto err_vdd_spkr; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err_vdd_spkr; } mutex_init(&cdc_mclk_mutex); ret = of_property_read_string(pdev->dev.of_node, "qcom,prim-auxpcm-gpio-set", &auxpcm_pri_gpio_set); if (ret) { dev_err(&pdev->dev, "Looking up %s property in node %s failed", "qcom,prim-auxpcm-gpio-set", pdev->dev.of_node->full_name); goto err_vdd_spkr; } if (!strcmp(auxpcm_pri_gpio_set, "prim-gpio-prim")) { lpaif_pri_muxsel_virt_addr = ioremap(LPAIF_PRI_MODE_MUXSEL, 4); } else if (!strcmp(auxpcm_pri_gpio_set, "prim-gpio-tert")) { lpaif_pri_muxsel_virt_addr = ioremap(LPAIF_TER_MODE_MUXSEL, 4); } else { dev_err(&pdev->dev, "Invalid value %s for AUXPCM GPIO set\n", auxpcm_pri_gpio_set); ret = -EINVAL; goto err_vdd_spkr; } if (lpaif_pri_muxsel_virt_addr == NULL) { pr_err("%s Pri muxsel virt addr is null\n", __func__); ret = -EINVAL; goto err_vdd_spkr; } return 0; err_vdd_spkr: if (vdd_spkr_gpio >= 0) { gpio_free(vdd_spkr_gpio); vdd_spkr_gpio = -1; } err: if (pdata->mclk_gpio > 0) { dev_dbg(&pdev->dev, "%s free gpio %d\n", __func__, pdata->mclk_gpio); gpio_free(pdata->mclk_gpio); pdata->mclk_gpio = 0; } devm_kfree(&pdev->dev, pdata); return ret; }
static int imx_wm8962_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct device_node *ssi_np, *codec_np; struct platform_device *ssi_pdev; struct imx_priv *priv = &card_priv; struct i2c_client *codec_dev; struct imx_wm8962_data *data; int int_port, ext_port; int ret; priv->pdev = pdev; ret = of_property_read_u32(np, "mux-int-port", &int_port); if (ret) { dev_err(&pdev->dev, "mux-int-port missing or invalid\n"); return ret; } ret = of_property_read_u32(np, "mux-ext-port", &ext_port); if (ret) { dev_err(&pdev->dev, "mux-ext-port missing or invalid\n"); return ret; } /* * The port numbering in the hardware manual starts at 1, while * the audmux API expects it starts at 0. */ int_port--; ext_port--; ret = imx_audmux_v2_configure_port(int_port, IMX_AUDMUX_V2_PTCR_SYN | IMX_AUDMUX_V2_PTCR_TFSEL(ext_port) | IMX_AUDMUX_V2_PTCR_TCSEL(ext_port) | IMX_AUDMUX_V2_PTCR_TFSDIR | IMX_AUDMUX_V2_PTCR_TCLKDIR, IMX_AUDMUX_V2_PDCR_RXDSEL(ext_port)); if (ret) { dev_err(&pdev->dev, "audmux internal port setup failed\n"); return ret; } ret = imx_audmux_v2_configure_port(ext_port, IMX_AUDMUX_V2_PTCR_SYN, IMX_AUDMUX_V2_PDCR_RXDSEL(int_port)); if (ret) { dev_err(&pdev->dev, "audmux external port setup failed\n"); return ret; } ssi_np = of_parse_phandle(pdev->dev.of_node, "ssi-controller", 0); codec_np = of_parse_phandle(pdev->dev.of_node, "audio-codec", 0); if (!ssi_np || !codec_np) { dev_err(&pdev->dev, "phandle missing or invalid\n"); ret = -EINVAL; goto fail; } ssi_pdev = of_find_device_by_node(ssi_np); if (!ssi_pdev) { dev_err(&pdev->dev, "failed to find SSI platform device\n"); ret = -EINVAL; goto fail; } codec_dev = of_find_i2c_device_by_node(codec_np); if (!codec_dev || !codec_dev->dev.driver) { dev_err(&pdev->dev, "failed to find codec platform device\n"); ret = -EINVAL; goto fail; } data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL); if (!data) { ret = -ENOMEM; goto fail; } data->codec_clk = devm_clk_get(&codec_dev->dev, NULL); if (IS_ERR(data->codec_clk)) { ret = PTR_ERR(data->codec_clk); dev_err(&codec_dev->dev, "failed to get codec clk: %d\n", ret); goto fail; } data->clk_frequency = clk_get_rate(data->codec_clk); ret = clk_prepare_enable(data->codec_clk); if (ret) { dev_err(&codec_dev->dev, "failed to enable codec clk: %d\n", ret); goto fail; } data->dai.name = "HiFi"; data->dai.stream_name = "HiFi"; data->dai.codec_dai_name = "wm8962"; data->dai.codec_of_node = codec_np; data->dai.cpu_dai_name = dev_name(&ssi_pdev->dev); data->dai.platform_of_node = ssi_np; data->dai.ops = &imx_hifi_ops; data->dai.dai_fmt = SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | SND_SOC_DAIFMT_CBM_CFM; data->card.dev = &pdev->dev; ret = snd_soc_of_parse_card_name(&data->card, "model"); if (ret) goto clk_fail; ret = snd_soc_of_parse_audio_routing(&data->card, "audio-routing"); if (ret) goto clk_fail; data->card.num_links = 1; data->card.owner = THIS_MODULE; data->card.dai_link = &data->dai; data->card.dapm_widgets = imx_wm8962_dapm_widgets; data->card.num_dapm_widgets = ARRAY_SIZE(imx_wm8962_dapm_widgets); data->card.late_probe = imx_wm8962_late_probe; data->card.set_bias_level = imx_wm8962_set_bias_level; platform_set_drvdata(pdev, &data->card); snd_soc_card_set_drvdata(&data->card, data); ret = devm_snd_soc_register_card(&pdev->dev, &data->card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto clk_fail; } of_node_put(ssi_np); of_node_put(codec_np); return 0; clk_fail: clk_disable_unprepare(data->codec_clk); fail: of_node_put(ssi_np); of_node_put(codec_np); return ret; }
static struct apq8016_sbc_data *apq8016_sbc_parse_of(struct snd_soc_card *card) { struct device *dev = card->dev; struct snd_soc_dai_link *link; struct device_node *np, *codec, *cpu, *node = dev->of_node; struct apq8016_sbc_data *data; int ret, num_links; ret = snd_soc_of_parse_card_name(card, "qcom,model"); if (ret) { dev_err(dev, "Error parsing card name: %d\n", ret); return ERR_PTR(ret); } /* DAPM routes */ if (of_property_read_bool(node, "qcom,audio-routing")) { ret = snd_soc_of_parse_audio_routing(card, "qcom,audio-routing"); if (ret) return ERR_PTR(ret); } /* Populate links */ num_links = of_get_child_count(node); /* Allocate the private data and the DAI link array */ data = devm_kzalloc(dev, sizeof(*data) + sizeof(*link) * num_links, GFP_KERNEL); if (!data) return ERR_PTR(-ENOMEM); card->dai_link = &data->dai_link[0]; card->num_links = num_links; link = data->dai_link; for_each_child_of_node(node, np) { cpu = of_get_child_by_name(np, "cpu"); codec = of_get_child_by_name(np, "codec"); if (!cpu || !codec) { dev_err(dev, "Can't find cpu/codec DT node\n"); return ERR_PTR(-EINVAL); } link->cpu_of_node = of_parse_phandle(cpu, "sound-dai", 0); if (!link->cpu_of_node) { dev_err(card->dev, "error getting cpu phandle\n"); return ERR_PTR(-EINVAL); } link->codec_of_node = of_parse_phandle(codec, "sound-dai", 0); if (!link->codec_of_node) { dev_err(card->dev, "error getting codec phandle\n"); return ERR_PTR(-EINVAL); } ret = snd_soc_of_get_dai_name(cpu, &link->cpu_dai_name); if (ret) { dev_err(card->dev, "error getting cpu dai name\n"); return ERR_PTR(ret); } ret = snd_soc_of_get_dai_name(codec, &link->codec_dai_name); if (ret) { dev_err(card->dev, "error getting codec dai name\n"); return ERR_PTR(ret); } link->platform_of_node = link->cpu_of_node; ret = of_property_read_string(np, "link-name", &link->name); if (ret) { dev_err(card->dev, "error getting codec dai_link name\n"); return ERR_PTR(ret); } link->stream_name = link->name; link->init = apq8016_sbc_dai_init; link++; }
static int tegra_sgtl5000_driver_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct snd_soc_card *card = &snd_soc_tegra_sgtl5000; struct tegra_sgtl5000 *machine; int ret; machine = devm_kzalloc(&pdev->dev, sizeof(struct tegra_sgtl5000), GFP_KERNEL); if (!machine) return -ENOMEM; card->dev = &pdev->dev; snd_soc_card_set_drvdata(card, machine); ret = snd_soc_of_parse_card_name(card, "nvidia,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "nvidia,audio-routing"); if (ret) goto err; tegra_sgtl5000_dai.codec_of_node = of_parse_phandle(np, "nvidia,audio-codec", 0); if (!tegra_sgtl5000_dai.codec_of_node) { dev_err(&pdev->dev, "Property 'nvidia,audio-codec' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_sgtl5000_dai.cpu_of_node = of_parse_phandle(np, "nvidia,i2s-controller", 0); if (!tegra_sgtl5000_dai.cpu_of_node) { dev_err(&pdev->dev, "Property 'nvidia,i2s-controller' missing/invalid\n"); ret = -EINVAL; goto err; } tegra_sgtl5000_dai.platform_of_node = tegra_sgtl5000_dai.cpu_of_node; ret = tegra_asoc_utils_init(&machine->util_data, &pdev->dev); if (ret) goto err; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err_fini_utils; } return 0; err_fini_utils: tegra_asoc_utils_fini(&machine->util_data); err: return ret; }
static int davinci_evm_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; const struct of_device_id *match; struct snd_soc_dai_link *dai; struct snd_soc_card_drvdata_davinci *drvdata = NULL; struct clk *mclk; int ret = 0; match = of_match_device(of_match_ptr(davinci_evm_dt_ids), &pdev->dev); if (!match) { dev_err(&pdev->dev, "Error: No device match found\n"); return -ENODEV; } dai = (struct snd_soc_dai_link *) match->data; evm_soc_card.dai_link = dai; dai->codec_of_node = of_parse_phandle(np, "ti,audio-codec", 0); if (!dai->codec_of_node) return -EINVAL; dai->cpu_of_node = of_parse_phandle(np, "ti,mcasp-controller", 0); if (!dai->cpu_of_node) return -EINVAL; dai->platform_of_node = dai->cpu_of_node; evm_soc_card.dev = &pdev->dev; ret = snd_soc_of_parse_card_name(&evm_soc_card, "ti,model"); if (ret) return ret; mclk = devm_clk_get(&pdev->dev, "mclk"); if (PTR_ERR(mclk) == -EPROBE_DEFER) { return -EPROBE_DEFER; } else if (IS_ERR(mclk)) { dev_dbg(&pdev->dev, "mclk not found.\n"); mclk = NULL; } drvdata = devm_kzalloc(&pdev->dev, sizeof(*drvdata), GFP_KERNEL); if (!drvdata) return -ENOMEM; drvdata->mclk = mclk; ret = of_property_read_u32(np, "ti,codec-clock-rate", &drvdata->sysclk); if (ret < 0) { if (!drvdata->mclk) { dev_err(&pdev->dev, "No clock or clock rate defined.\n"); return -EINVAL; } drvdata->sysclk = clk_get_rate(drvdata->mclk); } else if (drvdata->mclk) { unsigned int requestd_rate = drvdata->sysclk; clk_set_rate(drvdata->mclk, drvdata->sysclk); drvdata->sysclk = clk_get_rate(drvdata->mclk); if (drvdata->sysclk != requestd_rate) dev_warn(&pdev->dev, "Could not get requested rate %u using %u.\n", requestd_rate, drvdata->sysclk); } snd_soc_card_set_drvdata(&evm_soc_card, drvdata); ret = devm_snd_soc_register_card(&pdev->dev, &evm_soc_card); if (ret) dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); return ret; }
static int tegra_wm8903_driver_probe(struct platform_device *pdev) { struct device_node *np = pdev->dev.of_node; struct snd_soc_card *card = &snd_soc_tegra_wm8903; struct tegra_wm8903 *machine; int ret; machine = devm_kzalloc(&pdev->dev, sizeof(struct tegra_wm8903), GFP_KERNEL); if (!machine) { dev_err(&pdev->dev, "Can't allocate tegra_wm8903 struct\n"); return -ENOMEM; } card->dev = &pdev->dev; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, machine); machine->gpio_spkr_en = of_get_named_gpio(np, "nvidia,spkr-en-gpios", 0); if (machine->gpio_spkr_en == -EPROBE_DEFER) return -EPROBE_DEFER; if (gpio_is_valid(machine->gpio_spkr_en)) { ret = devm_gpio_request_one(&pdev->dev, machine->gpio_spkr_en, GPIOF_OUT_INIT_LOW, "spkr_en"); if (ret) { dev_err(card->dev, "cannot get spkr_en gpio\n"); return ret; } } machine->gpio_hp_mute = of_get_named_gpio(np, "nvidia,hp-mute-gpios", 0); if (machine->gpio_hp_mute == -EPROBE_DEFER) return -EPROBE_DEFER; if (gpio_is_valid(machine->gpio_hp_mute)) { ret = devm_gpio_request_one(&pdev->dev, machine->gpio_hp_mute, GPIOF_OUT_INIT_HIGH, "hp_mute"); if (ret) { dev_err(card->dev, "cannot get hp_mute gpio\n"); return ret; } } machine->gpio_hp_det = of_get_named_gpio(np, "nvidia,hp-det-gpios", 0); if (machine->gpio_hp_det == -EPROBE_DEFER) return -EPROBE_DEFER; machine->gpio_int_mic_en = of_get_named_gpio(np, "nvidia,int-mic-en-gpios", 0); if (machine->gpio_int_mic_en == -EPROBE_DEFER) return -EPROBE_DEFER; if (gpio_is_valid(machine->gpio_int_mic_en)) { /* Disable int mic; enable signal is active-high */ ret = devm_gpio_request_one(&pdev->dev, machine->gpio_int_mic_en, GPIOF_OUT_INIT_LOW, "int_mic_en"); if (ret) { dev_err(card->dev, "cannot get int_mic_en gpio\n"); return ret; } } machine->gpio_ext_mic_en = of_get_named_gpio(np, "nvidia,ext-mic-en-gpios", 0); if (machine->gpio_ext_mic_en == -EPROBE_DEFER) return -EPROBE_DEFER; if (gpio_is_valid(machine->gpio_ext_mic_en)) { /* Enable ext mic; enable signal is active-low */ ret = devm_gpio_request_one(&pdev->dev, machine->gpio_ext_mic_en, GPIOF_OUT_INIT_LOW, "ext_mic_en"); if (ret) { dev_err(card->dev, "cannot get ext_mic_en gpio\n"); return ret; } } ret = snd_soc_of_parse_card_name(card, "nvidia,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "nvidia,audio-routing"); if (ret) goto err; tegra_wm8903_dai.codec_of_node = of_parse_phandle(np, "nvidia,audio-codec", 0); if (!tegra_wm8903_dai.codec_of_node) { dev_err(&pdev->dev, "Property 'nvidia,audio-codec' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_wm8903_dai.cpu_of_node = of_parse_phandle(np, "nvidia,i2s-controller", 0); if (!tegra_wm8903_dai.cpu_of_node) { dev_err(&pdev->dev, "Property 'nvidia,i2s-controller' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_wm8903_dai.platform_of_node = tegra_wm8903_dai.cpu_of_node; ret = tegra_asoc_utils_init(&machine->util_data, &pdev->dev); if (ret) goto err; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err_fini_utils; } return 0; err_fini_utils: tegra_asoc_utils_fini(&machine->util_data); err: return ret; }
static __devinit int tegra_alc5632_probe(struct platform_device *pdev) { struct snd_soc_card *card = &snd_soc_tegra_alc5632; struct tegra_alc5632 *alc5632; int ret; alc5632 = devm_kzalloc(&pdev->dev, sizeof(struct tegra_alc5632), GFP_KERNEL); if (!alc5632) { dev_err(&pdev->dev, "Can't allocate tegra_alc5632\n"); ret = -ENOMEM; goto err; } card->dev = &pdev->dev; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, alc5632); alc5632->pcm_dev = ERR_PTR(-EINVAL); if (!(pdev->dev.of_node)) { dev_err(&pdev->dev, "Must be instantiated using device tree\n"); ret = -EINVAL; goto err; } ret = snd_soc_of_parse_card_name(card, "nvidia,model"); if (ret) goto err; ret = snd_soc_of_parse_audio_routing(card, "nvidia,audio-routing"); if (ret) goto err; tegra_alc5632_dai.codec_of_node = of_parse_phandle( pdev->dev.of_node, "nvidia,audio-codec", 0); if (!tegra_alc5632_dai.codec_of_node) { dev_err(&pdev->dev, "Property 'nvidia,audio-codec' missing or invalid\n"); ret = -EINVAL; goto err; } tegra_alc5632_dai.cpu_dai_of_node = of_parse_phandle( pdev->dev.of_node, "nvidia,i2s-controller", 0); if (!tegra_alc5632_dai.cpu_dai_of_node) { dev_err(&pdev->dev, "Property 'nvidia,i2s-controller' missing or invalid\n"); ret = -EINVAL; goto err; } alc5632->pcm_dev = platform_device_register_simple( "tegra-pcm-audio", -1, NULL, 0); if (IS_ERR(alc5632->pcm_dev)) { dev_err(&pdev->dev, "Can't instantiate tegra-pcm-audio\n"); ret = PTR_ERR(alc5632->pcm_dev); goto err; } ret = tegra_asoc_utils_init(&alc5632->util_data, &pdev->dev); if (ret) goto err_unregister; ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "snd_soc_register_card failed (%d)\n", ret); goto err_fini_utils; } return 0; err_fini_utils: tegra_asoc_utils_fini(&alc5632->util_data); err_unregister: if (!IS_ERR(alc5632->pcm_dev)) platform_device_unregister(alc5632->pcm_dev); err: return ret; }