brintos

brintos / linux-shallow public Read only

0
0
Text · 4.2 KiB · 9edd6d9 Raw
168 lines · c
1// SPDX-License-Identifier: GPL-2.0-only2// Copyright(c) 2015-18 Intel Corporation.3 4/*5 * Machine Driver for SKL+ platforms with DSP and iDisp, HDA Codecs6 */7 8#include <linux/module.h>9#include <linux/platform_device.h>10#include <sound/core.h>11#include <sound/hda_codec.h>12#include <sound/jack.h>13#include <sound/pcm.h>14#include <sound/pcm_params.h>15#include <sound/soc.h>16#include <sound/soc-acpi.h>17#include "../../codecs/hdac_hda.h"18#include "../../sof/intel/hda.h"19#include "sof_board_helpers.h"20 21static int skl_hda_card_late_probe(struct snd_soc_card *card)22{23	return sof_intel_board_card_late_probe(card);24}25 26#define HDA_CODEC_AUTOSUSPEND_DELAY_MS 100027 28static void skl_set_hda_codec_autosuspend_delay(struct snd_soc_card *card)29{30	struct snd_soc_pcm_runtime *rtd;31	struct hdac_hda_priv *hda_pvt;32	struct snd_soc_dai *dai;33 34	for_each_card_rtds(card, rtd) {35		if (!strstr(rtd->dai_link->codecs->name, "ehdaudio0D0"))36			continue;37		dai = snd_soc_rtd_to_codec(rtd, 0);38		hda_pvt = snd_soc_component_get_drvdata(dai->component);39		if (hda_pvt) {40			/*41			 * all codecs are on the same bus, so it's sufficient42			 * to look up only the first one43			 */44			snd_hda_set_power_save(hda_pvt->codec->bus,45					       HDA_CODEC_AUTOSUSPEND_DELAY_MS);46			break;47		}48	}49}50 51#define IDISP_HDMI_BE_ID	152#define HDA_BE_ID		453#define DMIC01_BE_ID		654#define DMIC16K_BE_ID		755#define BT_OFFLOAD_BE_ID	856 57#define HDA_LINK_ORDER	SOF_LINK_ORDER(SOF_LINK_IDISP_HDMI,  \58				       SOF_LINK_HDA,        \59				       SOF_LINK_DMIC01,     \60				       SOF_LINK_DMIC16K,    \61				       SOF_LINK_BT_OFFLOAD, \62				       SOF_LINK_NONE,       \63				       SOF_LINK_NONE)64 65#define HDA_LINK_IDS	SOF_LINK_ORDER(IDISP_HDMI_BE_ID,  \66				       HDA_BE_ID,        \67				       DMIC01_BE_ID,     \68				       DMIC16K_BE_ID,    \69				       BT_OFFLOAD_BE_ID, \70				       0,                \71				       0)72 73static unsigned long74skl_hda_get_board_quirk(struct snd_soc_acpi_mach_params *mach_params)75{76	unsigned long board_quirk = 0;77	int ssp_bt;78 79	if (hweight_long(mach_params->bt_link_mask) == 1) {80		ssp_bt = fls(mach_params->bt_link_mask) - 1;81		board_quirk |= SOF_SSP_PORT_BT_OFFLOAD(ssp_bt) |82				SOF_BT_OFFLOAD_PRESENT;83	}84 85	return board_quirk;86}87 88static int skl_hda_audio_probe(struct platform_device *pdev)89{90	struct snd_soc_acpi_mach *mach = pdev->dev.platform_data;91	struct sof_card_private *ctx;92	struct snd_soc_card *card;93	unsigned long board_quirk = skl_hda_get_board_quirk(&mach->mach_params);94	int ret;95 96	card = devm_kzalloc(&pdev->dev, sizeof(struct snd_soc_card), GFP_KERNEL);97	if (!card)98		return -ENOMEM;99 100	card->name = "hda-dsp";101	card->owner = THIS_MODULE;102	card->fully_routed = true;103	card->late_probe = skl_hda_card_late_probe;104 105	dev_dbg(&pdev->dev, "board_quirk = %lx\n", board_quirk);106 107	/* initialize ctx with board quirk */108	ctx = sof_intel_board_get_ctx(&pdev->dev, board_quirk);109	if (!ctx)110		return -ENOMEM;111 112	if (HDA_EXT_CODEC(mach->mach_params.codec_mask))113		ctx->hda_codec_present = true;114 115	if (mach->mach_params.codec_mask & IDISP_CODEC_MASK)116		ctx->hdmi.idisp_codec = true;117 118	ctx->link_order_overwrite = HDA_LINK_ORDER;119	ctx->link_id_overwrite = HDA_LINK_IDS;120 121	/* update dai_link */122	ret = sof_intel_board_set_dai_link(&pdev->dev, card, ctx);123	if (ret)124		return ret;125 126	card->dev = &pdev->dev;127	if (!snd_soc_acpi_sof_parent(&pdev->dev))128		card->disable_route_checks = true;129 130	if (mach->mach_params.dmic_num > 0) {131		card->components = devm_kasprintf(card->dev, GFP_KERNEL,132						  "cfg-dmics:%d",133						  mach->mach_params.dmic_num);134		if (!card->components)135			return -ENOMEM;136	}137 138	ret = snd_soc_fixup_dai_links_platform_name(card,139						    mach->mach_params.platform);140	if (ret)141		return ret;142 143	snd_soc_card_set_drvdata(card, ctx);144 145	ret = devm_snd_soc_register_card(&pdev->dev, card);146	if (!ret)147		skl_set_hda_codec_autosuspend_delay(card);148 149	return ret;150}151 152static struct platform_driver skl_hda_audio = {153	.probe = skl_hda_audio_probe,154	.driver = {155		.name = "skl_hda_dsp_generic",156		.pm = &snd_soc_pm_ops,157	},158};159 160module_platform_driver(skl_hda_audio)161 162/* Module information */163MODULE_DESCRIPTION("SKL/KBL/BXT/APL HDA Generic Machine driver");164MODULE_AUTHOR("Rakesh Ughreja <rakesh.a.ughreja@intel.com>");165MODULE_LICENSE("GPL v2");166MODULE_ALIAS("platform:skl_hda_dsp_generic");167MODULE_IMPORT_NS(SND_SOC_INTEL_SOF_BOARD_HELPERS);168