0001
0002
0003
0004
0005
0006
0007
0008 #include <sound/soc.h>
0009 #include <sound/soc-dapm.h>
0010 #include <linux/module.h>
0011 #include <sound/pcm.h>
0012 #include <sound/pcm_params.h>
0013 #include <linux/io.h>
0014 #include <linux/dmi.h>
0015 #include <linux/acpi.h>
0016
0017 #include "acp6x.h"
0018
0019 #define DRV_NAME "acp_yc_mach"
0020
0021 SND_SOC_DAILINK_DEF(acp6x_pdm,
0022 DAILINK_COMP_ARRAY(COMP_CPU("acp_yc_pdm_dma.0")));
0023
0024 SND_SOC_DAILINK_DEF(dmic_codec,
0025 DAILINK_COMP_ARRAY(COMP_CODEC("dmic-codec.0",
0026 "dmic-hifi")));
0027
0028 SND_SOC_DAILINK_DEF(pdm_platform,
0029 DAILINK_COMP_ARRAY(COMP_PLATFORM("acp_yc_pdm_dma.0")));
0030
0031 static struct snd_soc_dai_link acp6x_dai_pdm[] = {
0032 {
0033 .name = "acp6x-dmic-capture",
0034 .stream_name = "DMIC capture",
0035 .capture_only = 1,
0036 SND_SOC_DAILINK_REG(acp6x_pdm, dmic_codec, pdm_platform),
0037 },
0038 };
0039
0040 static struct snd_soc_card acp6x_card = {
0041 .name = "acp6x",
0042 .owner = THIS_MODULE,
0043 .dai_link = acp6x_dai_pdm,
0044 .num_links = 1,
0045 };
0046
0047 static const struct dmi_system_id yc_acp_quirk_table[] = {
0048 {
0049 .driver_data = &acp6x_card,
0050 .matches = {
0051 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0052 DMI_MATCH(DMI_PRODUCT_NAME, "21D2"),
0053 }
0054 },
0055 {
0056 .driver_data = &acp6x_card,
0057 .matches = {
0058 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0059 DMI_MATCH(DMI_PRODUCT_NAME, "21D3"),
0060 }
0061 },
0062 {
0063 .driver_data = &acp6x_card,
0064 .matches = {
0065 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0066 DMI_MATCH(DMI_PRODUCT_NAME, "21D4"),
0067 }
0068 },
0069 {
0070 .driver_data = &acp6x_card,
0071 .matches = {
0072 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0073 DMI_MATCH(DMI_PRODUCT_NAME, "21D5"),
0074 }
0075 },
0076 {
0077 .driver_data = &acp6x_card,
0078 .matches = {
0079 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0080 DMI_MATCH(DMI_PRODUCT_NAME, "21CF"),
0081 }
0082 },
0083 {
0084 .driver_data = &acp6x_card,
0085 .matches = {
0086 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0087 DMI_MATCH(DMI_PRODUCT_NAME, "21CG"),
0088 }
0089 },
0090 {
0091 .driver_data = &acp6x_card,
0092 .matches = {
0093 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0094 DMI_MATCH(DMI_PRODUCT_NAME, "21CQ"),
0095 }
0096 },
0097 {
0098 .driver_data = &acp6x_card,
0099 .matches = {
0100 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0101 DMI_MATCH(DMI_PRODUCT_NAME, "21CR"),
0102 }
0103 },
0104 {
0105 .driver_data = &acp6x_card,
0106 .matches = {
0107 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0108 DMI_MATCH(DMI_PRODUCT_NAME, "21CM"),
0109 }
0110 },
0111 {
0112 .driver_data = &acp6x_card,
0113 .matches = {
0114 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0115 DMI_MATCH(DMI_PRODUCT_NAME, "21CN"),
0116 }
0117 },
0118 {
0119 .driver_data = &acp6x_card,
0120 .matches = {
0121 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0122 DMI_MATCH(DMI_PRODUCT_NAME, "21CH"),
0123 }
0124 },
0125 {
0126 .driver_data = &acp6x_card,
0127 .matches = {
0128 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0129 DMI_MATCH(DMI_PRODUCT_NAME, "21CJ"),
0130 }
0131 },
0132 {
0133 .driver_data = &acp6x_card,
0134 .matches = {
0135 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0136 DMI_MATCH(DMI_PRODUCT_NAME, "21CK"),
0137 }
0138 },
0139 {
0140 .driver_data = &acp6x_card,
0141 .matches = {
0142 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0143 DMI_MATCH(DMI_PRODUCT_NAME, "21CL"),
0144 }
0145 },
0146 {
0147 .driver_data = &acp6x_card,
0148 .matches = {
0149 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0150 DMI_MATCH(DMI_PRODUCT_NAME, "21EM"),
0151 }
0152 },
0153 {
0154 .driver_data = &acp6x_card,
0155 .matches = {
0156 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0157 DMI_MATCH(DMI_PRODUCT_NAME, "21EN"),
0158 }
0159 },
0160 {
0161 .driver_data = &acp6x_card,
0162 .matches = {
0163 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0164 DMI_MATCH(DMI_PRODUCT_NAME, "21J5"),
0165 }
0166 },
0167 {
0168 .driver_data = &acp6x_card,
0169 .matches = {
0170 DMI_MATCH(DMI_BOARD_VENDOR, "LENOVO"),
0171 DMI_MATCH(DMI_PRODUCT_NAME, "21J6"),
0172 }
0173 },
0174 {}
0175 };
0176
0177 static int acp6x_probe(struct platform_device *pdev)
0178 {
0179 const struct dmi_system_id *dmi_id;
0180 struct acp6x_pdm *machine = NULL;
0181 struct snd_soc_card *card;
0182 struct acpi_device *adev;
0183 int ret;
0184
0185
0186 adev = ACPI_COMPANION(pdev->dev.parent);
0187 if (adev) {
0188 const union acpi_object *obj;
0189
0190 if (!acpi_dev_get_property(adev, "AcpDmicConnected", ACPI_TYPE_INTEGER, &obj) &&
0191 obj->integer.value == 1)
0192 platform_set_drvdata(pdev, &acp6x_card);
0193 }
0194
0195
0196 dmi_id = dmi_first_match(yc_acp_quirk_table);
0197 if (dmi_id)
0198 platform_set_drvdata(pdev, dmi_id->driver_data);
0199
0200 card = platform_get_drvdata(pdev);
0201 if (!card)
0202 return -ENODEV;
0203 dev_info(&pdev->dev, "Enabling ACP DMIC support via %s", dmi_id ? "DMI" : "ACPI");
0204 acp6x_card.dev = &pdev->dev;
0205
0206 snd_soc_card_set_drvdata(card, machine);
0207 ret = devm_snd_soc_register_card(&pdev->dev, card);
0208 if (ret) {
0209 return dev_err_probe(&pdev->dev, ret,
0210 "snd_soc_register_card(%s) failed\n",
0211 card->name);
0212 }
0213 return 0;
0214 }
0215
0216 static struct platform_driver acp6x_mach_driver = {
0217 .driver = {
0218 .name = "acp_yc_mach",
0219 .pm = &snd_soc_pm_ops,
0220 },
0221 .probe = acp6x_probe,
0222 };
0223
0224 module_platform_driver(acp6x_mach_driver);
0225
0226 MODULE_AUTHOR("Vijendar.Mukunda@amd.com");
0227 MODULE_LICENSE("GPL v2");
0228 MODULE_ALIAS("platform:" DRV_NAME);