On Fri, May 13, 2016 at 12:59 AM, nick83ola nick83ola@gmail.com wrote:
Caleb thanks for your help!!!! the documentation is really orrible!!!!
but now I'm getting something out of TXD!!!!
Wooo!
only no clock and very fast (I think that I need to configure the oscillator/pll and iomux???)
Right, I wish I understood how to do that. I don't. It's got something to do with some function called 'clock' I bet :-) Or maybe 'clk'. Or maybe in the DTS and not a function call...
In my kernel (3.14.28-1.0.0_ga+g91cf351) some of the statement in you dts are not supported in simple driver so I stripped down the imx-si476 driver and use with your dummy codec driver
Yeah, that's the problem with old kernels. I try to just look towards the future :-)
I'm glad things are working, and thanks for posting your working DTS. Having your DTS here may help the next guy with an old kernel.
Cheers -Caleb
&audmux { pinctrl-names = "default"; pinctrl-0 = <&pinctrl_audmux_4>; status = "okay"; };
&ssi2 { assigned-clocks = <&clks IMX6QDL_CLK_SSI2_SEL>; assigned-clock-parents = <&clks IMX6QDL_CLK_PLL4_AUDIO_DIV>; assigned-clock-rates = <0>; fsl,mode = "i2s-master"; status = "okay"; };
/ { model = "Engicam i.CoreM6 DualLite/Solo starterkit"; compatible = "fsl,imx6-icore", "fsl,imx6dl";
codec_test: codec_test { compatible = "linux,snd-soc-dummy"; status = "okay"; }; sound { compatible = "fsl,imx-audio-itel"; model = "imx-itel"; ssi-controller = <&ssi2>; audio-codec = <&codec_test>; mux-int-port = <4>; mux-ext-port = <2>; status = "okay"; }; sound-hdmi { status = "disabled"; };
};
&iomuxc { audmux { pinctrl_audmux_4: audmux-4 { fsl,pins = < MX6QDL_PAD_DISP0_DAT20__AUD4_TXC 0x130b0 MX6QDL_PAD_DISP0_DAT21__AUD4_TXD 0x110b0 MX6QDL_PAD_DISP0_DAT22__AUD4_TXFS 0x130b0 MX6QDL_PAD_DISP0_DAT23__AUD4_RXD 0x130b0 >; }; }; };
====================================================================================================================== imx-itel.c
======================================================================================================================
/*
- Copyright (C) 2013 Freescale Semiconductor, Inc.
- The code contained herein is licensed under the GNU General Public
- License. You may obtain a copy of the GNU General Public License
- Version 2 or later at the following locations:
- http://www.opensource.org/licenses/gpl-license.html
- http://www.gnu.org/copyleft/gpl.html
*/
#define DEBUG 1
#include <linux/module.h> #include <linux/of.h> #include <linux/of_platform.h> #include <linux/device.h> #include <linux/clk.h> #include <sound/core.h> #include <sound/pcm.h> #include <sound/soc.h> #include <sound/initval.h> #include <sound/pcm_params.h>
#include "imx-audmux.h"
struct imx_itel_data { struct snd_soc_dai_link dai; struct snd_soc_card card; };
static int imx_audmux_config(int slave, int master) { unsigned int ptcr, pdcr; slave = slave - 1; master = master - 1;
ptcr = IMX_AUDMUX_V2_PTCR_SYN | IMX_AUDMUX_V2_PTCR_TFSDIR | IMX_AUDMUX_V2_PTCR_TFSEL(slave) | IMX_AUDMUX_V2_PTCR_TCLKDIR | IMX_AUDMUX_V2_PTCR_TCSEL(slave); pdcr = IMX_AUDMUX_V2_PDCR_RXDSEL(slave); imx_audmux_v2_configure_port(master, ptcr, pdcr); /* * According to RM, RCLKDIR and SYN should not be changed at same time. * So separate to two step for configuring this port. */ ptcr |= IMX_AUDMUX_V2_PTCR_RFSDIR | IMX_AUDMUX_V2_PTCR_RFSEL(slave) | IMX_AUDMUX_V2_PTCR_RCLKDIR | IMX_AUDMUX_V2_PTCR_RCSEL(slave); imx_audmux_v2_configure_port(master, ptcr, pdcr); printk(KERN_ERR "--> ITEL imx-audmux-confic ext-port port=%#010x
ptcr=%#010x pdcr=%#010x\n", master, ptcr, pdcr);
ptcr = IMX_AUDMUX_V2_PTCR_SYN; pdcr = IMX_AUDMUX_V2_PDCR_RXDSEL(master); printk(KERN_ERR "--> ITEL imx-audmux-config int-port port=%#010x
ptcr=%#010x pdcr=%#010x\n", master, ptcr, pdcr); imx_audmux_v2_configure_port(slave, ptcr, pdcr);
return 0;
}
static int imx_itel_hw_params(struct snd_pcm_substream *substream, struct snd_pcm_hw_params *params) { struct snd_soc_pcm_runtime *rtd = substream->private_data; struct snd_soc_dai *cpu_dai = rtd->cpu_dai; u32 channels = params_channels(params); u32 rate = params_rate(params); u32 bclk = rate * channels * 32; int ret = 0;
printk(KERN_ERR "--> ITEL imx-itel-hw-params NAME=%s \n VALUE=%#010x
" "SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | SND_SOC_DAIFMT_CBS_CFS\n", cpu_dai->name, (SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | SND_SOC_DAIFMT_CBS_CFS));
/* set cpu DAI configuration */ ret = snd_soc_dai_set_fmt(cpu_dai, SND_SOC_DAIFMT_I2S | SND_SOC_DAIFMT_NB_NF | SND_SOC_DAIFMT_CBS_CFS); if (ret) { dev_err(cpu_dai->dev, "failed to set dai fmt\n"); return ret; } printk(KERN_ERR "--> ITEL imx-itel-hw-params set tdm slots
channels=%d", channels);
ret = snd_soc_dai_set_tdm_slot(cpu_dai, channels == 1 ? 0xfffffffe : 0xfffffffc, channels == 1 ? 0xfffffffe : 0xfffffffc, 2, 32); if (ret) { dev_err(cpu_dai->dev, "failed to set dai tdm slot\n"); return ret; } printk(KERN_ERR "--> ITEL imx-audmux-config set sysclk NAME=%s
\n",cpu_dai->name);
ret = snd_soc_dai_set_sysclk(cpu_dai, 0, bclk, SND_SOC_CLOCK_OUT); if (ret) dev_err(cpu_dai->dev, "failed to set sysclk\n"); return ret;
}
static struct snd_soc_ops imx_itel_ops = { .hw_params = imx_itel_hw_params, };
static struct snd_soc_dai_link imx_itel_dai[] = { { .name = "Hifi", .stream_name = "Hifi", .codec_dai_name = "snd-soc-dummy-dai", //.codec_name = "snd-soc-dummy", .ops = &imx_itel_ops, // .symmetric_rates = 1, }, };
static struct snd_soc_card snd_soc_card_imx_itel = { .name = "imx-audio-itel", .dai_link = imx_itel_dai, .num_links = ARRAY_SIZE(imx_itel_dai), .owner = THIS_MODULE, };
static int imx_itel_probe(struct platform_device *pdev) { struct snd_soc_card *card = &snd_soc_card_imx_itel; struct device_node *ssi_np; struct platform_device *ssi_pdev; struct device_node *codec_np; // struct imx_itel_data *data = NULL; int int_port, ext_port, ret;
printk(KERN_ERR "--> ITEL imx_itel_probe"); ret = of_property_read_u32(pdev->dev.of_node, "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(pdev->dev.of_node, "mux-ext-port",
&ext_port); if (ret) { dev_err(&pdev->dev, "mux-ext-port missing or invalid\n"); return ret; }
printk(KERN_ERR "--> ITEL Configuro audmux\n"); imx_audmux_config(int_port, ext_port); /* find value in devicetree for ssi controller */ 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 = -EINVAL; goto fail; } /* find SSI platform driver */ ssi_pdev = of_find_device_by_node(ssi_np); if (!ssi_pdev) { dev_err(&pdev->dev, "failed to find SSI platform device\n"); ret = -EPROBE_DEFER; goto fail; } codec_np = of_parse_phandle(pdev->dev.of_node, "audio-codec", 0); if (!codec_np) { dev_err(&pdev->dev, "codec missing or invalid\n"); ret = -EINVAL; goto fail; } // codec_dev = NULL; card->dev = &pdev->dev; card->dai_link->cpu_dai_name = dev_name(&ssi_pdev->dev); card->dai_link->platform_of_node = ssi_np; card->dai_link->codec_of_node = codec_np; platform_set_drvdata(pdev, card); snd_soc_card_set_drvdata(card, &snd_soc_card_imx_itel); printk(KERN_ERR "--> ITEL imx-probe registro card\n"); ret = snd_soc_register_card(card); if (ret) { dev_err(&pdev->dev, "Failed to register card: %d\n", ret); goto fail; } printk(KERN_ERR "--> ITEL imx-probe of ssi\n"); of_node_put(ssi_np); printk(KERN_ERR "--> ITEL imx-probe of codec\n"); of_node_put(codec_np); return 0;
fail: if (ssi_np) of_node_put(ssi_np); if (codec_np) of_node_put(codec_np);
return ret;
}
static int imx_itel_remove(struct platform_device *pdev) { struct snd_soc_card *card = &snd_soc_card_imx_itel;
snd_soc_unregister_card(card); return 0;
}
static const struct of_device_id imx_itel_dt_ids[] = { { .compatible = "fsl,imx-audio-itel", }, { /* sentinel */ } }; MODULE_DEVICE_TABLE(of, imx_itel_dt_ids);
static struct platform_driver imx_itel_driver = { .driver = { .name = "imx-itel", .owner = THIS_MODULE, .pm = &snd_soc_pm_ops, .of_match_table = imx_itel_dt_ids, }, .probe = imx_itel_probe, .remove = imx_itel_remove, };
module_platform_driver(imx_itel_driver);
MODULE_AUTHOR("Nicola Lunghi"); MODULE_DESCRIPTION("ITEL I2S Platform Driver"); MODULE_LICENSE("GPL v2"); MODULE_ALIAS("platform:imx-itel");
2016-05-12 9:55 GMT+02:00 nick83ola nick83ola@gmail.com:
I am using ssi1 because I have an example of setting master mode on sabre board dts
I have a problem with iomux/pinctrl I think because
root@icorem6solo:/sys/kernel/debug/pinctrl/20e0000.iomuxc# cat pinmux-pins |grep audmux pin 57 (MX6DL_PAD_DISP0_DAT20): 2028000.ssi (GPIO UNCLAIMED) function audmux group audmux-4 pin 58 (MX6DL_PAD_DISP0_DAT21): 2028000.ssi (GPIO UNCLAIMED) function audmux group audmux-4 pin 59 (MX6DL_PAD_DISP0_DAT22): 2028000.ssi (GPIO UNCLAIMED) function audmux group audmux-4 pin 60 (MX6DL_PAD_DISP0_DAT23): 2028000.ssi (GPIO UNCLAIMED) function audmux group audmux-4
says: GPIO_UNCLAIMED? it is correct??
/sys/kernel/debug/pinctrl/20e0000.iomuxc# cat pinconf-groups |grep -A 1 audmux 1 (audmux-1): MX6DL_PAD_SD2_DAT0: 0x17070MX6DL_PAD_SD2_DAT3: 0x17070MX6DL_PAD_SD2_DAT2: 0x17070MX6DL_PAD_SD2_DAT1: 0x17070 2 (audmux-2): MX6DL_PAD_CSI0_DAT7: 0x1b0b0MX6DL_PAD_CSI0_DAT4: 0x1b0b0MX6DL_PAD_CSI0_DAT5: 0x1b0b0MX6DL_PAD_CSI0_DAT6: 0x1b0b0 3 (audmux-3): MX6DL_PAD_DISP0_DAT16: 0x10MX6DL_PAD_DISP0_DAT18: 0x1b0b0MX6DL_PAD_DISP0_DAT19: 0x1b0b0 4 (audmux-4): MX6DL_PAD_DISP0_DAT20: 0x130b0MX6DL_PAD_DISP0_DAT21: 0x110b0MX6DL_PAD_DISP0_DAT22: 0x130b0MX6DL_PAD_DISP0_DAT23: 0x130b0
0x130b0?
audmux# cat ssi0 PDCR: 0000a000 PTCR: ad400800 TxFS output from SSI6, TxClk output from SSI6 Port is symmetric Data received from SSI6 root@icorem6solo:/sys/kernel/debug/audmux# cat ssi1 PDCR: 00008000 PTCR: 00000800 TxFS input, TxClk input Port is symmetric Data received from SSI5 root@icorem6solo:/sys/kernel/debug/audmux# cat ssi2 PDCR: 00006000 PTCR: 9cc00800 TxFS output from SSI4, TxClk output from SSI4 Port is symmetric Data received from SSI4 root@icorem6solo:/sys/kernel/debug/audmux# cat ssi3 PDCR: 00004000 PTCR: 00000800 TxFS input, TxClk input Port is symmetric Data received from SSI3 root@icorem6solo:/sys/kernel/debug/audmux# cat ssi4 PDCR: 00002000 PTCR: 8c400800 TxFS output from imx-ssi.1, TxClk output from imx-ssi.1 Port is symmetric Data received from imx-ssi.1 root@icorem6solo:/sys/kernel/debug/audmux# cat ssi5 PDCR: 00000000 PTCR: 00000800 TxFS input, TxClk input Port is symmetric Data received from imx-ssi.0 root@icorem6solo:/sys/kernel/debug/audmux# cat ssi6 PDCR: 0000c000 PTCR: 00000800 TxFS input, TxClk input Port is symmetric Data received from UNKNOWN
--
P.S. Le informazioni trasmesse attraverso la presente comunicazione sono di esclusiva spettanza dell'effettivo destinatario. Nel caso in cui le stesse raggiungessero, per qualunque motivo, soggetti non interessati, questi ultimi vorranno darne immediata notizia al mittente. In ogni caso, eventuali soggetti diversi dai legittimi destinatari della presente comunicazione e dei dati contenuti negli allegati, possono essere sanzionati ai sensi del T.U. sul trattamento dei dati personali d.lgs. 196/2003, sia ai sensi dell'art. 616 del Codice Penale che disciplina la violazione del segreto sulla corrispondenza.