Path: blob/master/sound/soc/mediatek/mt8195/mt8195-mt6359.c
26488 views
// SPDX-License-Identifier: GPL-2.01/*2* mt8195-mt6359.c --3* MT8195-MT6359 ALSA SoC machine driver code4*5* Copyright (c) 2022 MediaTek Inc.6* Author: Trevor Wu <[email protected]>7* YC Hung <[email protected]>8*/910#include <linux/input.h>11#include <linux/module.h>12#include <linux/of.h>13#include <linux/pm_runtime.h>14#include <sound/jack.h>15#include <sound/pcm_params.h>16#include <sound/rt5682.h>17#include <sound/soc.h>18#include "../../codecs/mt6359.h"19#include "../../codecs/rt1011.h"20#include "../../codecs/rt5682.h"21#include "../common/mtk-afe-platform-driver.h"22#include "../common/mtk-dsp-sof-common.h"23#include "../common/mtk-soc-card.h"24#include "../common/mtk-soundcard-driver.h"25#include "mt8195-afe-clk.h"26#include "mt8195-afe-common.h"2728#define RT1011_SPEAKER_AMP_PRESENT BIT(0)29#define RT1019_SPEAKER_AMP_PRESENT BIT(1)30#define MAX98390_SPEAKER_AMP_PRESENT BIT(2)3132#define DUMB_CODEC_INIT BIT(0)33#define MT6359_CODEC_INIT BIT(1)34#define RT1011_CODEC_INIT BIT(2)35#define RT1019_CODEC_INIT BIT(3)36#define MAX98390_CODEC_INIT BIT(4)37#define RT5682_CODEC_INIT BIT(5)3839#define RT1011_CODEC_DAI "rt1011-aif"40#define RT1011_DEV0_NAME "rt1011.2-0038"41#define RT1011_DEV1_NAME "rt1011.2-0039"4243#define RT1019_CODEC_DAI "HiFi"44#define RT1019_DEV0_NAME "rt1019p"4546#define MAX98390_CODEC_DAI "max98390-aif1"47#define MAX98390_DEV0_NAME "max98390.2-0038" /* right */48#define MAX98390_DEV1_NAME "max98390.2-0039" /* left */4950#define RT5682_CODEC_DAI "rt5682-aif1"51#define RT5682_DEV0_NAME "rt5682.2-001a"5253#define RT5682S_CODEC_DAI "rt5682s-aif1"54#define RT5682S_DEV0_NAME "rt5682s.2-001a"5556#define SOF_DMA_DL2 "SOF_DMA_DL2"57#define SOF_DMA_DL3 "SOF_DMA_DL3"58#define SOF_DMA_UL4 "SOF_DMA_UL4"59#define SOF_DMA_UL5 "SOF_DMA_UL5"6061struct mt8195_mt6359_priv {62struct clk *i2so1_mclk;63};6465enum mt8195_jacks {66MT8195_JACK_HEADSET,67MT8195_JACK_DP,68MT8195_JACK_HDMI,69MT8195_JACK_MAX,70};7172/* Headset jack detection DAPM pins */73static struct snd_soc_jack_pin mt8195_jack_pins[] = {74{75.pin = "Headphone",76.mask = SND_JACK_HEADPHONE,77},78{79.pin = "Headset Mic",80.mask = SND_JACK_MICROPHONE,81},82};8384static const struct snd_soc_dapm_widget mt8195_mt6359_widgets[] = {85SND_SOC_DAPM_HP("Headphone", NULL),86SND_SOC_DAPM_MIC("Headset Mic", NULL),87SND_SOC_DAPM_MIXER(SOF_DMA_DL2, SND_SOC_NOPM, 0, 0, NULL, 0),88SND_SOC_DAPM_MIXER(SOF_DMA_DL3, SND_SOC_NOPM, 0, 0, NULL, 0),89SND_SOC_DAPM_MIXER(SOF_DMA_UL4, SND_SOC_NOPM, 0, 0, NULL, 0),90SND_SOC_DAPM_MIXER(SOF_DMA_UL5, SND_SOC_NOPM, 0, 0, NULL, 0),91};9293static const struct snd_soc_dapm_route mt8195_mt6359_routes[] = {94/* SOF Uplink */95{SOF_DMA_UL4, NULL, "O034"},96{SOF_DMA_UL4, NULL, "O035"},97{SOF_DMA_UL5, NULL, "O036"},98{SOF_DMA_UL5, NULL, "O037"},99/* SOF Downlink */100{"I070", NULL, SOF_DMA_DL2},101{"I071", NULL, SOF_DMA_DL2},102{"I020", NULL, SOF_DMA_DL3},103{"I021", NULL, SOF_DMA_DL3},104};105106static const struct snd_kcontrol_new mt8195_mt6359_controls[] = {107SOC_DAPM_PIN_SWITCH("Headphone"),108SOC_DAPM_PIN_SWITCH("Headset Mic"),109};110111static const struct snd_soc_dapm_widget mt8195_dual_speaker_widgets[] = {112SND_SOC_DAPM_SPK("Left Spk", NULL),113SND_SOC_DAPM_SPK("Right Spk", NULL),114};115116static const struct snd_kcontrol_new mt8195_dual_speaker_controls[] = {117SOC_DAPM_PIN_SWITCH("Left Spk"),118SOC_DAPM_PIN_SWITCH("Right Spk"),119};120121static const struct snd_soc_dapm_widget mt8195_speaker_widgets[] = {122SND_SOC_DAPM_SPK("Ext Spk", NULL),123};124125static const struct snd_kcontrol_new mt8195_speaker_controls[] = {126SOC_DAPM_PIN_SWITCH("Ext Spk"),127};128129static const struct snd_soc_dapm_route mt8195_rt5682_routes[] = {130/* headset */131{ "Headphone", NULL, "HPOL" },132{ "Headphone", NULL, "HPOR" },133{ "IN1P", NULL, "Headset Mic" },134};135136static const struct snd_soc_dapm_route mt8195_rt1011_routes[] = {137{ "Left Spk", NULL, "Left SPO" },138{ "Right Spk", NULL, "Right SPO" },139};140141static const struct snd_soc_dapm_route mt8195_rt1019_routes[] = {142{ "Ext Spk", NULL, "Speaker" },143};144145static const struct snd_soc_dapm_route mt8195_max98390_routes[] = {146{ "Left Spk", NULL, "Left BE_OUT" },147{ "Right Spk", NULL, "Right BE_OUT" },148};149150#define CKSYS_AUD_TOP_CFG 0x032c151#define CKSYS_AUD_TOP_MON 0x0330152153static int mt8195_mt6359_mtkaif_calibration(struct snd_soc_pcm_runtime *rtd)154{155struct snd_soc_component *cmpnt_afe =156snd_soc_rtdcom_lookup(rtd, AFE_PCM_NAME);157struct snd_soc_component *cmpnt_codec =158snd_soc_rtd_to_codec(rtd, 0)->component;159struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt_afe);160struct mt8195_afe_private *afe_priv = afe->platform_priv;161struct mtkaif_param *param = &afe_priv->mtkaif_params;162int chosen_phase_1, chosen_phase_2, chosen_phase_3;163int prev_cycle_1, prev_cycle_2, prev_cycle_3;164int test_done_1, test_done_2, test_done_3;165int cycle_1, cycle_2, cycle_3;166int mtkaif_chosen_phase[MT8195_MTKAIF_MISO_NUM];167int mtkaif_phase_cycle[MT8195_MTKAIF_MISO_NUM];168int mtkaif_calibration_num_phase;169bool mtkaif_calibration_ok;170unsigned int monitor = 0;171int counter;172int phase;173int i;174175dev_dbg(afe->dev, "%s(), start\n", __func__);176177param->mtkaif_calibration_ok = false;178for (i = 0; i < MT8195_MTKAIF_MISO_NUM; i++) {179param->mtkaif_chosen_phase[i] = -1;180param->mtkaif_phase_cycle[i] = 0;181mtkaif_chosen_phase[i] = -1;182mtkaif_phase_cycle[i] = 0;183}184185if (IS_ERR(afe_priv->topckgen)) {186dev_info(afe->dev, "%s() Cannot find topckgen controller\n",187__func__);188return 0;189}190191pm_runtime_get_sync(afe->dev);192mt6359_mtkaif_calibration_enable(cmpnt_codec);193194/* set test type to synchronizer pulse */195regmap_update_bits(afe_priv->topckgen,196CKSYS_AUD_TOP_CFG, 0xffff, 0x4);197mtkaif_calibration_num_phase = 42; /* mt6359: 0 ~ 42 */198mtkaif_calibration_ok = true;199200for (phase = 0;201phase <= mtkaif_calibration_num_phase && mtkaif_calibration_ok;202phase++) {203mt6359_set_mtkaif_calibration_phase(cmpnt_codec,204phase, phase, phase);205206regmap_update_bits(afe_priv->topckgen,207CKSYS_AUD_TOP_CFG, 0x1, 0x1);208209test_done_1 = 0;210test_done_2 = 0;211test_done_3 = 0;212cycle_1 = -1;213cycle_2 = -1;214cycle_3 = -1;215counter = 0;216while (!(test_done_1 & test_done_2 & test_done_3)) {217regmap_read(afe_priv->topckgen,218CKSYS_AUD_TOP_MON, &monitor);219test_done_1 = (monitor >> 28) & 0x1;220test_done_2 = (monitor >> 29) & 0x1;221test_done_3 = (monitor >> 30) & 0x1;222if (test_done_1 == 1)223cycle_1 = monitor & 0xf;224225if (test_done_2 == 1)226cycle_2 = (monitor >> 4) & 0xf;227228if (test_done_3 == 1)229cycle_3 = (monitor >> 8) & 0xf;230231/* handle if never test done */232if (++counter > 10000) {233dev_info(afe->dev, "%s(), test fail, cycle_1 %d, cycle_2 %d, cycle_3 %d, monitor 0x%x\n",234__func__,235cycle_1, cycle_2, cycle_3, monitor);236mtkaif_calibration_ok = false;237break;238}239}240241if (phase == 0) {242prev_cycle_1 = cycle_1;243prev_cycle_2 = cycle_2;244prev_cycle_3 = cycle_3;245}246247if (cycle_1 != prev_cycle_1 &&248mtkaif_chosen_phase[MT8195_MTKAIF_MISO_0] < 0) {249mtkaif_chosen_phase[MT8195_MTKAIF_MISO_0] = phase - 1;250mtkaif_phase_cycle[MT8195_MTKAIF_MISO_0] = prev_cycle_1;251}252253if (cycle_2 != prev_cycle_2 &&254mtkaif_chosen_phase[MT8195_MTKAIF_MISO_1] < 0) {255mtkaif_chosen_phase[MT8195_MTKAIF_MISO_1] = phase - 1;256mtkaif_phase_cycle[MT8195_MTKAIF_MISO_1] = prev_cycle_2;257}258259if (cycle_3 != prev_cycle_3 &&260mtkaif_chosen_phase[MT8195_MTKAIF_MISO_2] < 0) {261mtkaif_chosen_phase[MT8195_MTKAIF_MISO_2] = phase - 1;262mtkaif_phase_cycle[MT8195_MTKAIF_MISO_2] = prev_cycle_3;263}264265regmap_update_bits(afe_priv->topckgen,266CKSYS_AUD_TOP_CFG, 0x1, 0x0);267268if (mtkaif_chosen_phase[MT8195_MTKAIF_MISO_0] >= 0 &&269mtkaif_chosen_phase[MT8195_MTKAIF_MISO_1] >= 0 &&270mtkaif_chosen_phase[MT8195_MTKAIF_MISO_2] >= 0)271break;272}273274if (mtkaif_chosen_phase[MT8195_MTKAIF_MISO_0] < 0) {275mtkaif_calibration_ok = false;276chosen_phase_1 = 0;277} else {278chosen_phase_1 = mtkaif_chosen_phase[MT8195_MTKAIF_MISO_0];279}280281if (mtkaif_chosen_phase[MT8195_MTKAIF_MISO_1] < 0) {282mtkaif_calibration_ok = false;283chosen_phase_2 = 0;284} else {285chosen_phase_2 = mtkaif_chosen_phase[MT8195_MTKAIF_MISO_1];286}287288if (mtkaif_chosen_phase[MT8195_MTKAIF_MISO_2] < 0) {289mtkaif_calibration_ok = false;290chosen_phase_3 = 0;291} else {292chosen_phase_3 = mtkaif_chosen_phase[MT8195_MTKAIF_MISO_2];293}294295mt6359_set_mtkaif_calibration_phase(cmpnt_codec,296chosen_phase_1,297chosen_phase_2,298chosen_phase_3);299300mt6359_mtkaif_calibration_disable(cmpnt_codec);301pm_runtime_put(afe->dev);302303param->mtkaif_calibration_ok = mtkaif_calibration_ok;304param->mtkaif_chosen_phase[MT8195_MTKAIF_MISO_0] = chosen_phase_1;305param->mtkaif_chosen_phase[MT8195_MTKAIF_MISO_1] = chosen_phase_2;306param->mtkaif_chosen_phase[MT8195_MTKAIF_MISO_2] = chosen_phase_3;307for (i = 0; i < MT8195_MTKAIF_MISO_NUM; i++)308param->mtkaif_phase_cycle[i] = mtkaif_phase_cycle[i];309310dev_info(afe->dev, "%s(), end, calibration ok %d\n",311__func__, param->mtkaif_calibration_ok);312313return 0;314}315316static int mt8195_mt6359_init(struct snd_soc_pcm_runtime *rtd)317{318struct snd_soc_component *cmpnt_codec =319snd_soc_rtd_to_codec(rtd, 0)->component;320321/* set mtkaif protocol */322mt6359_set_mtkaif_protocol(cmpnt_codec,323MT6359_MTKAIF_PROTOCOL_2_CLK_P2);324325/* mtkaif calibration */326mt8195_mt6359_mtkaif_calibration(rtd);327328return 0;329}330331static int mt8195_hdmitx_dptx_startup(struct snd_pcm_substream *substream)332{333return mtk_soundcard_startup(substream, MTK_CONSTRAINT_HDMIDP);334}335336static const struct snd_soc_ops mt8195_hdmitx_dptx_playback_ops = {337.startup = mt8195_hdmitx_dptx_startup,338};339340static int mt8195_dptx_hw_params(struct snd_pcm_substream *substream,341struct snd_pcm_hw_params *params)342{343struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);344struct snd_soc_dai *cpu_dai = snd_soc_rtd_to_cpu(rtd, 0);345346return snd_soc_dai_set_sysclk(cpu_dai, 0, params_rate(params) * 256,347SND_SOC_CLOCK_OUT);348}349350static const struct snd_soc_ops mt8195_dptx_ops = {351.hw_params = mt8195_dptx_hw_params,352};353354static int mt8195_dptx_codec_init(struct snd_soc_pcm_runtime *rtd)355{356struct mtk_soc_card_data *soc_card_data = snd_soc_card_get_drvdata(rtd->card);357struct snd_soc_jack *jack = &soc_card_data->card_data->jacks[MT8195_JACK_DP];358struct snd_soc_component *cmpnt_codec =359snd_soc_rtd_to_codec(rtd, 0)->component;360int ret;361362ret = snd_soc_card_jack_new(rtd->card, "DP Jack", SND_JACK_LINEOUT, jack);363if (ret)364return ret;365366return snd_soc_component_set_jack(cmpnt_codec, jack, NULL);367}368369static int mt8195_hdmi_codec_init(struct snd_soc_pcm_runtime *rtd)370{371struct mtk_soc_card_data *soc_card_data = snd_soc_card_get_drvdata(rtd->card);372struct snd_soc_jack *jack = &soc_card_data->card_data->jacks[MT8195_JACK_HDMI];373struct snd_soc_component *cmpnt_codec =374snd_soc_rtd_to_codec(rtd, 0)->component;375int ret;376377ret = snd_soc_card_jack_new(rtd->card, "HDMI Jack", SND_JACK_LINEOUT, jack);378if (ret)379return ret;380381return snd_soc_component_set_jack(cmpnt_codec, jack, NULL);382}383384static int mt8195_dptx_hw_params_fixup(struct snd_soc_pcm_runtime *rtd,385struct snd_pcm_hw_params *params)386{387/* fix BE i2s format to S24_LE, clean param mask first */388snd_mask_reset_range(hw_param_mask(params, SNDRV_PCM_HW_PARAM_FORMAT),3890, (__force unsigned int)SNDRV_PCM_FORMAT_LAST);390391params_set_format(params, SNDRV_PCM_FORMAT_S24_LE);392393return 0;394}395396static int mt8195_rt5682_etdm_hw_params(struct snd_pcm_substream *substream,397struct snd_pcm_hw_params *params)398{399struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);400struct snd_soc_card *card = rtd->card;401struct snd_soc_dai *cpu_dai = snd_soc_rtd_to_cpu(rtd, 0);402struct snd_soc_dai *codec_dai = snd_soc_rtd_to_codec(rtd, 0);403unsigned int rate = params_rate(params);404int bitwidth;405int ret;406407bitwidth = snd_pcm_format_width(params_format(params));408if (bitwidth < 0) {409dev_err(card->dev, "invalid bit width: %d\n", bitwidth);410return bitwidth;411}412413ret = snd_soc_dai_set_tdm_slot(codec_dai, 0x00, 0x0, 0x2, bitwidth);414if (ret) {415dev_err(card->dev, "failed to set tdm slot\n");416return ret;417}418419ret = snd_soc_dai_set_pll(codec_dai, RT5682_PLL1, RT5682_PLL1_S_MCLK,420rate * 256, rate * 512);421if (ret) {422dev_err(card->dev, "failed to set pll\n");423return ret;424}425426ret = snd_soc_dai_set_sysclk(codec_dai, RT5682_SCLK_S_PLL1,427rate * 512, SND_SOC_CLOCK_IN);428if (ret) {429dev_err(card->dev, "failed to set sysclk\n");430return ret;431}432433return snd_soc_dai_set_sysclk(cpu_dai, 0, rate * 256,434SND_SOC_CLOCK_OUT);435}436437static const struct snd_soc_ops mt8195_rt5682_etdm_ops = {438.hw_params = mt8195_rt5682_etdm_hw_params,439};440441static int mt8195_rt5682_init(struct snd_soc_pcm_runtime *rtd)442{443struct snd_soc_component *cmpnt_codec =444snd_soc_rtd_to_codec(rtd, 0)->component;445struct mtk_soc_card_data *soc_card_data = snd_soc_card_get_drvdata(rtd->card);446struct mt8195_mt6359_priv *priv = soc_card_data->mach_priv;447struct snd_soc_jack *jack = &soc_card_data->card_data->jacks[MT8195_JACK_HEADSET];448struct snd_soc_component *cmpnt_afe =449snd_soc_rtdcom_lookup(rtd, AFE_PCM_NAME);450struct mtk_base_afe *afe = snd_soc_component_get_drvdata(cmpnt_afe);451struct mt8195_afe_private *afe_priv = afe->platform_priv;452struct snd_soc_card *card = rtd->card;453int ret;454455priv->i2so1_mclk = afe_priv->clk[MT8195_CLK_TOP_APLL12_DIV2];456457ret = snd_soc_card_jack_new_pins(rtd->card, "Headset Jack",458SND_JACK_HEADSET | SND_JACK_BTN_0 |459SND_JACK_BTN_1 | SND_JACK_BTN_2 |460SND_JACK_BTN_3,461jack, mt8195_jack_pins,462ARRAY_SIZE(mt8195_jack_pins));463if (ret) {464dev_err(rtd->dev, "Headset Jack creation failed: %d\n", ret);465return ret;466}467468snd_jack_set_key(jack->jack, SND_JACK_BTN_0, KEY_PLAYPAUSE);469snd_jack_set_key(jack->jack, SND_JACK_BTN_1, KEY_VOICECOMMAND);470snd_jack_set_key(jack->jack, SND_JACK_BTN_2, KEY_VOLUMEUP);471snd_jack_set_key(jack->jack, SND_JACK_BTN_3, KEY_VOLUMEDOWN);472473ret = snd_soc_component_set_jack(cmpnt_codec, jack, NULL);474if (ret) {475dev_err(rtd->dev, "Headset Jack set failed: %d\n", ret);476return ret;477}478479ret = snd_soc_dapm_add_routes(&card->dapm, mt8195_rt5682_routes,480ARRAY_SIZE(mt8195_rt5682_routes));481if (ret)482dev_err(rtd->dev, "unable to add dapm routes, ret %d\n", ret);483484return ret;485};486487static int mt8195_rt1011_etdm_hw_params(struct snd_pcm_substream *substream,488struct snd_pcm_hw_params *params)489{490struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);491struct snd_soc_dai *codec_dai;492struct snd_soc_card *card = rtd->card;493int srate, i, ret;494495srate = params_rate(params);496497for_each_rtd_codec_dais(rtd, i, codec_dai) {498ret = snd_soc_dai_set_pll(codec_dai, 0, RT1011_PLL1_S_BCLK,49964 * srate, 256 * srate);500if (ret < 0) {501dev_err(card->dev, "codec_dai clock not set\n");502return ret;503}504505ret = snd_soc_dai_set_sysclk(codec_dai,506RT1011_FS_SYS_PRE_S_PLL1,507256 * srate, SND_SOC_CLOCK_IN);508if (ret < 0) {509dev_err(card->dev, "codec_dai clock not set\n");510return ret;511}512}513return 0;514}515516static const struct snd_soc_ops mt8195_rt1011_etdm_ops = {517.hw_params = mt8195_rt1011_etdm_hw_params,518};519520static int mt8195_sof_be_hw_params(struct snd_pcm_substream *substream,521struct snd_pcm_hw_params *params)522{523struct snd_soc_pcm_runtime *rtd = snd_soc_substream_to_rtd(substream);524struct snd_soc_component *cmpnt_afe = NULL;525struct snd_soc_pcm_runtime *runtime;526527/* find afe component */528for_each_card_rtds(rtd->card, runtime) {529cmpnt_afe = snd_soc_rtdcom_lookup(runtime, AFE_PCM_NAME);530if (cmpnt_afe)531break;532}533534if (cmpnt_afe && !pm_runtime_active(cmpnt_afe->dev)) {535dev_err(rtd->dev, "afe pm runtime is not active!!\n");536return -EINVAL;537}538539return 0;540}541542static const struct snd_soc_ops mt8195_sof_be_ops = {543.hw_params = mt8195_sof_be_hw_params,544};545546static int mt8195_rt1011_init(struct snd_soc_pcm_runtime *rtd)547{548struct snd_soc_card *card = rtd->card;549int ret;550551ret = snd_soc_dapm_new_controls(&card->dapm, mt8195_dual_speaker_widgets,552ARRAY_SIZE(mt8195_dual_speaker_widgets));553if (ret) {554dev_err(rtd->dev, "unable to add dapm controls, ret %d\n", ret);555/* Don't need to add routes if widget addition failed */556return ret;557}558559ret = snd_soc_add_card_controls(card, mt8195_dual_speaker_controls,560ARRAY_SIZE(mt8195_dual_speaker_controls));561if (ret) {562dev_err(rtd->dev, "unable to add card controls, ret %d\n", ret);563return ret;564}565566ret = snd_soc_dapm_add_routes(&card->dapm, mt8195_rt1011_routes,567ARRAY_SIZE(mt8195_rt1011_routes));568if (ret)569dev_err(rtd->dev, "unable to add dapm routes, ret %d\n", ret);570571return ret;572}573574static int mt8195_dumb_amp_init(struct snd_soc_pcm_runtime *rtd)575{576struct snd_soc_card *card = rtd->card;577int ret;578579ret = snd_soc_dapm_new_controls(&card->dapm, mt8195_speaker_widgets,580ARRAY_SIZE(mt8195_speaker_widgets));581if (ret) {582dev_err(rtd->dev, "unable to add dapm controls, ret %d\n", ret);583/* Don't need to add routes if widget addition failed */584return ret;585}586587ret = snd_soc_add_card_controls(card, mt8195_speaker_controls,588ARRAY_SIZE(mt8195_speaker_controls));589if (ret) {590dev_err(rtd->dev, "unable to add card controls, ret %d\n", ret);591return ret;592}593594return 0;595}596597static int mt8195_rt1019_init(struct snd_soc_pcm_runtime *rtd)598{599struct snd_soc_card *card = rtd->card;600int ret;601602ret = mt8195_dumb_amp_init(rtd);603if (ret)604return ret;605606ret = snd_soc_dapm_add_routes(&card->dapm, mt8195_rt1019_routes,607ARRAY_SIZE(mt8195_rt1019_routes));608if (ret)609dev_err(rtd->dev, "unable to add dapm routes, ret %d\n", ret);610611return ret;612}613614static int mt8195_max98390_init(struct snd_soc_pcm_runtime *rtd)615{616struct snd_soc_card *card = rtd->card;617int ret;618619ret = snd_soc_dapm_new_controls(&card->dapm, mt8195_dual_speaker_widgets,620ARRAY_SIZE(mt8195_dual_speaker_widgets));621if (ret) {622dev_err(rtd->dev, "unable to add dapm controls, ret %d\n", ret);623/* Don't need to add routes if widget addition failed */624return ret;625}626627ret = snd_soc_add_card_controls(card, mt8195_dual_speaker_controls,628ARRAY_SIZE(mt8195_dual_speaker_controls));629if (ret) {630dev_err(rtd->dev, "unable to add card controls, ret %d\n", ret);631return ret;632}633634ret = snd_soc_dapm_add_routes(&card->dapm, mt8195_max98390_routes,635ARRAY_SIZE(mt8195_max98390_routes));636if (ret)637dev_err(rtd->dev, "unable to add dapm routes, ret %d\n", ret);638639return ret;640}641642static int mt8195_etdm_hw_params_fixup(struct snd_soc_pcm_runtime *rtd,643struct snd_pcm_hw_params *params)644{645/* fix BE i2s format to S24_LE, clean param mask first */646snd_mask_reset_range(hw_param_mask(params, SNDRV_PCM_HW_PARAM_FORMAT),6470, (__force unsigned int)SNDRV_PCM_FORMAT_LAST);648649params_set_format(params, SNDRV_PCM_FORMAT_S24_LE);650651return 0;652}653654static int mt8195_set_bias_level_post(struct snd_soc_card *card,655struct snd_soc_dapm_context *dapm, enum snd_soc_bias_level level)656{657struct snd_soc_component *component = dapm->component;658struct mtk_soc_card_data *soc_card_data = snd_soc_card_get_drvdata(card);659struct mt8195_mt6359_priv *priv = soc_card_data->mach_priv;660int ret;661662/*663* It's required to control mclk directly in the set_bias_level_post664* function for rt5682 and rt5682s codec, or the unexpected pop happens665* at the end of playback.666*/667if (!component ||668(strcmp(component->name, RT5682_DEV0_NAME) &&669strcmp(component->name, RT5682S_DEV0_NAME)))670return 0;671672switch (level) {673case SND_SOC_BIAS_OFF:674if (!__clk_is_enabled(priv->i2so1_mclk))675return 0;676677clk_disable_unprepare(priv->i2so1_mclk);678dev_dbg(card->dev, "Disable i2so1 mclk\n");679break;680case SND_SOC_BIAS_ON:681ret = clk_prepare_enable(priv->i2so1_mclk);682if (ret) {683dev_err(card->dev, "Can't enable i2so1 mclk: %d\n", ret);684return ret;685}686dev_dbg(card->dev, "Enable i2so1 mclk\n");687break;688default:689break;690}691692return 0;693}694695enum {696DAI_LINK_DL2_FE,697DAI_LINK_DL3_FE,698DAI_LINK_DL6_FE,699DAI_LINK_DL7_FE,700DAI_LINK_DL8_FE,701DAI_LINK_DL10_FE,702DAI_LINK_DL11_FE,703DAI_LINK_UL1_FE,704DAI_LINK_UL2_FE,705DAI_LINK_UL3_FE,706DAI_LINK_UL4_FE,707DAI_LINK_UL5_FE,708DAI_LINK_UL6_FE,709DAI_LINK_UL8_FE,710DAI_LINK_UL9_FE,711DAI_LINK_UL10_FE,712DAI_LINK_DL_SRC_BE,713DAI_LINK_DPTX_BE,714DAI_LINK_ETDM1_IN_BE,715DAI_LINK_ETDM2_IN_BE,716DAI_LINK_ETDM1_OUT_BE,717DAI_LINK_ETDM2_OUT_BE,718DAI_LINK_ETDM3_OUT_BE,719DAI_LINK_PCM1_BE,720DAI_LINK_UL_SRC1_BE,721DAI_LINK_UL_SRC2_BE,722DAI_LINK_REGULAR_LAST = DAI_LINK_UL_SRC2_BE,723DAI_LINK_SOF_START,724DAI_LINK_SOF_DL2_BE = DAI_LINK_SOF_START,725DAI_LINK_SOF_DL3_BE,726DAI_LINK_SOF_UL4_BE,727DAI_LINK_SOF_UL5_BE,728DAI_LINK_SOF_END = DAI_LINK_SOF_UL5_BE,729};730731#define DAI_LINK_REGULAR_NUM (DAI_LINK_REGULAR_LAST + 1)732733/* FE */734SND_SOC_DAILINK_DEFS(DL2_FE,735DAILINK_COMP_ARRAY(COMP_CPU("DL2")),736DAILINK_COMP_ARRAY(COMP_DUMMY()),737DAILINK_COMP_ARRAY(COMP_EMPTY()));738739SND_SOC_DAILINK_DEFS(DL3_FE,740DAILINK_COMP_ARRAY(COMP_CPU("DL3")),741DAILINK_COMP_ARRAY(COMP_DUMMY()),742DAILINK_COMP_ARRAY(COMP_EMPTY()));743744SND_SOC_DAILINK_DEFS(DL6_FE,745DAILINK_COMP_ARRAY(COMP_CPU("DL6")),746DAILINK_COMP_ARRAY(COMP_DUMMY()),747DAILINK_COMP_ARRAY(COMP_EMPTY()));748749SND_SOC_DAILINK_DEFS(DL7_FE,750DAILINK_COMP_ARRAY(COMP_CPU("DL7")),751DAILINK_COMP_ARRAY(COMP_DUMMY()),752DAILINK_COMP_ARRAY(COMP_EMPTY()));753754SND_SOC_DAILINK_DEFS(DL8_FE,755DAILINK_COMP_ARRAY(COMP_CPU("DL8")),756DAILINK_COMP_ARRAY(COMP_DUMMY()),757DAILINK_COMP_ARRAY(COMP_EMPTY()));758759SND_SOC_DAILINK_DEFS(DL10_FE,760DAILINK_COMP_ARRAY(COMP_CPU("DL10")),761DAILINK_COMP_ARRAY(COMP_DUMMY()),762DAILINK_COMP_ARRAY(COMP_EMPTY()));763764SND_SOC_DAILINK_DEFS(DL11_FE,765DAILINK_COMP_ARRAY(COMP_CPU("DL11")),766DAILINK_COMP_ARRAY(COMP_DUMMY()),767DAILINK_COMP_ARRAY(COMP_EMPTY()));768769SND_SOC_DAILINK_DEFS(UL1_FE,770DAILINK_COMP_ARRAY(COMP_CPU("UL1")),771DAILINK_COMP_ARRAY(COMP_DUMMY()),772DAILINK_COMP_ARRAY(COMP_EMPTY()));773774SND_SOC_DAILINK_DEFS(UL2_FE,775DAILINK_COMP_ARRAY(COMP_CPU("UL2")),776DAILINK_COMP_ARRAY(COMP_DUMMY()),777DAILINK_COMP_ARRAY(COMP_EMPTY()));778779SND_SOC_DAILINK_DEFS(UL3_FE,780DAILINK_COMP_ARRAY(COMP_CPU("UL3")),781DAILINK_COMP_ARRAY(COMP_DUMMY()),782DAILINK_COMP_ARRAY(COMP_EMPTY()));783784SND_SOC_DAILINK_DEFS(UL4_FE,785DAILINK_COMP_ARRAY(COMP_CPU("UL4")),786DAILINK_COMP_ARRAY(COMP_DUMMY()),787DAILINK_COMP_ARRAY(COMP_EMPTY()));788789SND_SOC_DAILINK_DEFS(UL5_FE,790DAILINK_COMP_ARRAY(COMP_CPU("UL5")),791DAILINK_COMP_ARRAY(COMP_DUMMY()),792DAILINK_COMP_ARRAY(COMP_EMPTY()));793794SND_SOC_DAILINK_DEFS(UL6_FE,795DAILINK_COMP_ARRAY(COMP_CPU("UL6")),796DAILINK_COMP_ARRAY(COMP_DUMMY()),797DAILINK_COMP_ARRAY(COMP_EMPTY()));798799SND_SOC_DAILINK_DEFS(UL8_FE,800DAILINK_COMP_ARRAY(COMP_CPU("UL8")),801DAILINK_COMP_ARRAY(COMP_DUMMY()),802DAILINK_COMP_ARRAY(COMP_EMPTY()));803804SND_SOC_DAILINK_DEFS(UL9_FE,805DAILINK_COMP_ARRAY(COMP_CPU("UL9")),806DAILINK_COMP_ARRAY(COMP_DUMMY()),807DAILINK_COMP_ARRAY(COMP_EMPTY()));808809SND_SOC_DAILINK_DEFS(UL10_FE,810DAILINK_COMP_ARRAY(COMP_CPU("UL10")),811DAILINK_COMP_ARRAY(COMP_DUMMY()),812DAILINK_COMP_ARRAY(COMP_EMPTY()));813814/* BE */815SND_SOC_DAILINK_DEFS(DL_SRC_BE,816DAILINK_COMP_ARRAY(COMP_CPU("DL_SRC")),817DAILINK_COMP_ARRAY(COMP_CODEC("mt6359-sound",818"mt6359-snd-codec-aif1")),819DAILINK_COMP_ARRAY(COMP_EMPTY()));820821SND_SOC_DAILINK_DEFS(DPTX_BE,822DAILINK_COMP_ARRAY(COMP_CPU("DPTX")),823DAILINK_COMP_ARRAY(COMP_DUMMY()),824DAILINK_COMP_ARRAY(COMP_EMPTY()));825826SND_SOC_DAILINK_DEFS(ETDM1_IN_BE,827DAILINK_COMP_ARRAY(COMP_CPU("ETDM1_IN")),828DAILINK_COMP_ARRAY(COMP_DUMMY()),829DAILINK_COMP_ARRAY(COMP_EMPTY()));830831SND_SOC_DAILINK_DEFS(ETDM2_IN_BE,832DAILINK_COMP_ARRAY(COMP_CPU("ETDM2_IN")),833DAILINK_COMP_ARRAY(COMP_DUMMY()),834DAILINK_COMP_ARRAY(COMP_EMPTY()));835836SND_SOC_DAILINK_DEFS(ETDM1_OUT_BE,837DAILINK_COMP_ARRAY(COMP_CPU("ETDM1_OUT")),838DAILINK_COMP_ARRAY(COMP_DUMMY()),839DAILINK_COMP_ARRAY(COMP_EMPTY()));840841SND_SOC_DAILINK_DEFS(ETDM2_OUT_BE,842DAILINK_COMP_ARRAY(COMP_CPU("ETDM2_OUT")),843DAILINK_COMP_ARRAY(COMP_DUMMY()),844DAILINK_COMP_ARRAY(COMP_EMPTY()));845846SND_SOC_DAILINK_DEFS(ETDM3_OUT_BE,847DAILINK_COMP_ARRAY(COMP_CPU("ETDM3_OUT")),848DAILINK_COMP_ARRAY(COMP_DUMMY()),849DAILINK_COMP_ARRAY(COMP_EMPTY()));850851SND_SOC_DAILINK_DEFS(PCM1_BE,852DAILINK_COMP_ARRAY(COMP_CPU("PCM1")),853DAILINK_COMP_ARRAY(COMP_DUMMY()),854DAILINK_COMP_ARRAY(COMP_EMPTY()));855856SND_SOC_DAILINK_DEFS(UL_SRC1_BE,857DAILINK_COMP_ARRAY(COMP_CPU("UL_SRC1")),858DAILINK_COMP_ARRAY(COMP_CODEC("mt6359-sound",859"mt6359-snd-codec-aif1"),860COMP_CODEC("dmic-codec",861"dmic-hifi")),862DAILINK_COMP_ARRAY(COMP_EMPTY()));863864SND_SOC_DAILINK_DEFS(UL_SRC2_BE,865DAILINK_COMP_ARRAY(COMP_CPU("UL_SRC2")),866DAILINK_COMP_ARRAY(COMP_CODEC("mt6359-sound",867"mt6359-snd-codec-aif2")),868DAILINK_COMP_ARRAY(COMP_EMPTY()));869870SND_SOC_DAILINK_DEFS(AFE_SOF_DL2,871DAILINK_COMP_ARRAY(COMP_CPU("SOF_DL2")),872DAILINK_COMP_ARRAY(COMP_DUMMY()),873DAILINK_COMP_ARRAY(COMP_EMPTY()));874875SND_SOC_DAILINK_DEFS(AFE_SOF_DL3,876DAILINK_COMP_ARRAY(COMP_CPU("SOF_DL3")),877DAILINK_COMP_ARRAY(COMP_DUMMY()),878DAILINK_COMP_ARRAY(COMP_EMPTY()));879880SND_SOC_DAILINK_DEFS(AFE_SOF_UL4,881DAILINK_COMP_ARRAY(COMP_CPU("SOF_UL4")),882DAILINK_COMP_ARRAY(COMP_DUMMY()),883DAILINK_COMP_ARRAY(COMP_EMPTY()));884885SND_SOC_DAILINK_DEFS(AFE_SOF_UL5,886DAILINK_COMP_ARRAY(COMP_CPU("SOF_UL5")),887DAILINK_COMP_ARRAY(COMP_DUMMY()),888DAILINK_COMP_ARRAY(COMP_EMPTY()));889890/* codec */891SND_SOC_DAILINK_DEF(rt1019_comps,892DAILINK_COMP_ARRAY(COMP_CODEC(RT1019_DEV0_NAME,893RT1019_CODEC_DAI)));894895SND_SOC_DAILINK_DEF(rt1011_comps,896DAILINK_COMP_ARRAY(COMP_CODEC(RT1011_DEV0_NAME,897RT1011_CODEC_DAI),898COMP_CODEC(RT1011_DEV1_NAME,899RT1011_CODEC_DAI)));900901SND_SOC_DAILINK_DEF(max98390_comps,902DAILINK_COMP_ARRAY(COMP_CODEC(MAX98390_DEV0_NAME,903MAX98390_CODEC_DAI),904COMP_CODEC(MAX98390_DEV1_NAME,905MAX98390_CODEC_DAI)));906907static const struct sof_conn_stream g_sof_conn_streams[] = {908{ "ETDM2_OUT_BE", "AFE_SOF_DL2", SOF_DMA_DL2, SNDRV_PCM_STREAM_PLAYBACK},909{ "ETDM1_OUT_BE", "AFE_SOF_DL3", SOF_DMA_DL3, SNDRV_PCM_STREAM_PLAYBACK},910{ "UL_SRC1_BE", "AFE_SOF_UL4", SOF_DMA_UL4, SNDRV_PCM_STREAM_CAPTURE},911{ "ETDM2_IN_BE", "AFE_SOF_UL5", SOF_DMA_UL5, SNDRV_PCM_STREAM_CAPTURE},912};913914static struct snd_soc_dai_link mt8195_mt6359_dai_links[] = {915/* FE */916[DAI_LINK_DL2_FE] = {917.name = "DL2_FE",918.stream_name = "DL2 Playback",919.trigger = {920SND_SOC_DPCM_TRIGGER_POST,921SND_SOC_DPCM_TRIGGER_POST,922},923.dynamic = 1,924.playback_only = 1,925.ops = &mtk_soundcard_common_playback_ops,926SND_SOC_DAILINK_REG(DL2_FE),927},928[DAI_LINK_DL3_FE] = {929.name = "DL3_FE",930.stream_name = "DL3 Playback",931.trigger = {932SND_SOC_DPCM_TRIGGER_POST,933SND_SOC_DPCM_TRIGGER_POST,934},935.dynamic = 1,936.playback_only = 1,937.ops = &mtk_soundcard_common_playback_ops,938SND_SOC_DAILINK_REG(DL3_FE),939},940[DAI_LINK_DL6_FE] = {941.name = "DL6_FE",942.stream_name = "DL6 Playback",943.trigger = {944SND_SOC_DPCM_TRIGGER_POST,945SND_SOC_DPCM_TRIGGER_POST,946},947.dynamic = 1,948.playback_only = 1,949.ops = &mtk_soundcard_common_playback_ops,950SND_SOC_DAILINK_REG(DL6_FE),951},952[DAI_LINK_DL7_FE] = {953.name = "DL7_FE",954.stream_name = "DL7 Playback",955.trigger = {956SND_SOC_DPCM_TRIGGER_PRE,957SND_SOC_DPCM_TRIGGER_PRE,958},959.dynamic = 1,960.playback_only = 1,961SND_SOC_DAILINK_REG(DL7_FE),962},963[DAI_LINK_DL8_FE] = {964.name = "DL8_FE",965.stream_name = "DL8 Playback",966.trigger = {967SND_SOC_DPCM_TRIGGER_POST,968SND_SOC_DPCM_TRIGGER_POST,969},970.dynamic = 1,971.playback_only = 1,972.ops = &mtk_soundcard_common_playback_ops,973SND_SOC_DAILINK_REG(DL8_FE),974},975[DAI_LINK_DL10_FE] = {976.name = "DL10_FE",977.stream_name = "DL10 Playback",978.trigger = {979SND_SOC_DPCM_TRIGGER_POST,980SND_SOC_DPCM_TRIGGER_POST,981},982.dynamic = 1,983.playback_only = 1,984.ops = &mt8195_hdmitx_dptx_playback_ops,985SND_SOC_DAILINK_REG(DL10_FE),986},987[DAI_LINK_DL11_FE] = {988.name = "DL11_FE",989.stream_name = "DL11 Playback",990.trigger = {991SND_SOC_DPCM_TRIGGER_POST,992SND_SOC_DPCM_TRIGGER_POST,993},994.dynamic = 1,995.playback_only = 1,996.ops = &mtk_soundcard_common_playback_ops,997SND_SOC_DAILINK_REG(DL11_FE),998},999[DAI_LINK_UL1_FE] = {1000.name = "UL1_FE",1001.stream_name = "UL1 Capture",1002.trigger = {1003SND_SOC_DPCM_TRIGGER_PRE,1004SND_SOC_DPCM_TRIGGER_PRE,1005},1006.dynamic = 1,1007.capture_only = 1,1008SND_SOC_DAILINK_REG(UL1_FE),1009},1010[DAI_LINK_UL2_FE] = {1011.name = "UL2_FE",1012.stream_name = "UL2 Capture",1013.trigger = {1014SND_SOC_DPCM_TRIGGER_POST,1015SND_SOC_DPCM_TRIGGER_POST,1016},1017.dynamic = 1,1018.capture_only = 1,1019.ops = &mtk_soundcard_common_capture_ops,1020SND_SOC_DAILINK_REG(UL2_FE),1021},1022[DAI_LINK_UL3_FE] = {1023.name = "UL3_FE",1024.stream_name = "UL3 Capture",1025.trigger = {1026SND_SOC_DPCM_TRIGGER_POST,1027SND_SOC_DPCM_TRIGGER_POST,1028},1029.dynamic = 1,1030.capture_only = 1,1031.ops = &mtk_soundcard_common_capture_ops,1032SND_SOC_DAILINK_REG(UL3_FE),1033},1034[DAI_LINK_UL4_FE] = {1035.name = "UL4_FE",1036.stream_name = "UL4 Capture",1037.trigger = {1038SND_SOC_DPCM_TRIGGER_POST,1039SND_SOC_DPCM_TRIGGER_POST,1040},1041.dynamic = 1,1042.capture_only = 1,1043.ops = &mtk_soundcard_common_capture_ops,1044SND_SOC_DAILINK_REG(UL4_FE),1045},1046[DAI_LINK_UL5_FE] = {1047.name = "UL5_FE",1048.stream_name = "UL5 Capture",1049.trigger = {1050SND_SOC_DPCM_TRIGGER_POST,1051SND_SOC_DPCM_TRIGGER_POST,1052},1053.dynamic = 1,1054.capture_only = 1,1055.ops = &mtk_soundcard_common_capture_ops,1056SND_SOC_DAILINK_REG(UL5_FE),1057},1058[DAI_LINK_UL6_FE] = {1059.name = "UL6_FE",1060.stream_name = "UL6 Capture",1061.trigger = {1062SND_SOC_DPCM_TRIGGER_PRE,1063SND_SOC_DPCM_TRIGGER_PRE,1064},1065.dynamic = 1,1066.capture_only = 1,1067SND_SOC_DAILINK_REG(UL6_FE),1068},1069[DAI_LINK_UL8_FE] = {1070.name = "UL8_FE",1071.stream_name = "UL8 Capture",1072.trigger = {1073SND_SOC_DPCM_TRIGGER_POST,1074SND_SOC_DPCM_TRIGGER_POST,1075},1076.dynamic = 1,1077.capture_only = 1,1078.ops = &mtk_soundcard_common_capture_ops,1079SND_SOC_DAILINK_REG(UL8_FE),1080},1081[DAI_LINK_UL9_FE] = {1082.name = "UL9_FE",1083.stream_name = "UL9 Capture",1084.trigger = {1085SND_SOC_DPCM_TRIGGER_POST,1086SND_SOC_DPCM_TRIGGER_POST,1087},1088.dynamic = 1,1089.capture_only = 1,1090.ops = &mtk_soundcard_common_capture_ops,1091SND_SOC_DAILINK_REG(UL9_FE),1092},1093[DAI_LINK_UL10_FE] = {1094.name = "UL10_FE",1095.stream_name = "UL10 Capture",1096.trigger = {1097SND_SOC_DPCM_TRIGGER_POST,1098SND_SOC_DPCM_TRIGGER_POST,1099},1100.dynamic = 1,1101.capture_only = 1,1102.ops = &mtk_soundcard_common_capture_ops,1103SND_SOC_DAILINK_REG(UL10_FE),1104},1105/* BE */1106[DAI_LINK_DL_SRC_BE] = {1107.name = "DL_SRC_BE",1108.no_pcm = 1,1109.playback_only = 1,1110SND_SOC_DAILINK_REG(DL_SRC_BE),1111},1112[DAI_LINK_DPTX_BE] = {1113.name = "DPTX_BE",1114.no_pcm = 1,1115.playback_only = 1,1116.ops = &mt8195_dptx_ops,1117.be_hw_params_fixup = mt8195_dptx_hw_params_fixup,1118SND_SOC_DAILINK_REG(DPTX_BE),1119},1120[DAI_LINK_ETDM1_IN_BE] = {1121.name = "ETDM1_IN_BE",1122.no_pcm = 1,1123.dai_fmt = SND_SOC_DAIFMT_I2S |1124SND_SOC_DAIFMT_NB_NF |1125SND_SOC_DAIFMT_CBC_CFC,1126.capture_only = 1,1127SND_SOC_DAILINK_REG(ETDM1_IN_BE),1128},1129[DAI_LINK_ETDM2_IN_BE] = {1130.name = "ETDM2_IN_BE",1131.no_pcm = 1,1132.dai_fmt = SND_SOC_DAIFMT_I2S |1133SND_SOC_DAIFMT_NB_NF |1134SND_SOC_DAIFMT_CBC_CFC,1135.capture_only = 1,1136.be_hw_params_fixup = mt8195_etdm_hw_params_fixup,1137SND_SOC_DAILINK_REG(ETDM2_IN_BE),1138},1139[DAI_LINK_ETDM1_OUT_BE] = {1140.name = "ETDM1_OUT_BE",1141.no_pcm = 1,1142.dai_fmt = SND_SOC_DAIFMT_I2S |1143SND_SOC_DAIFMT_NB_NF |1144SND_SOC_DAIFMT_CBC_CFC,1145.playback_only = 1,1146.be_hw_params_fixup = mt8195_etdm_hw_params_fixup,1147SND_SOC_DAILINK_REG(ETDM1_OUT_BE),1148},1149[DAI_LINK_ETDM2_OUT_BE] = {1150.name = "ETDM2_OUT_BE",1151.no_pcm = 1,1152.dai_fmt = SND_SOC_DAIFMT_I2S |1153SND_SOC_DAIFMT_NB_NF |1154SND_SOC_DAIFMT_CBC_CFC,1155.playback_only = 1,1156SND_SOC_DAILINK_REG(ETDM2_OUT_BE),1157},1158[DAI_LINK_ETDM3_OUT_BE] = {1159.name = "ETDM3_OUT_BE",1160.no_pcm = 1,1161.dai_fmt = SND_SOC_DAIFMT_I2S |1162SND_SOC_DAIFMT_NB_NF |1163SND_SOC_DAIFMT_CBC_CFC,1164.playback_only = 1,1165SND_SOC_DAILINK_REG(ETDM3_OUT_BE),1166},1167[DAI_LINK_PCM1_BE] = {1168.name = "PCM1_BE",1169.no_pcm = 1,1170.dai_fmt = SND_SOC_DAIFMT_I2S |1171SND_SOC_DAIFMT_NB_NF |1172SND_SOC_DAIFMT_CBC_CFC,1173SND_SOC_DAILINK_REG(PCM1_BE),1174},1175[DAI_LINK_UL_SRC1_BE] = {1176.name = "UL_SRC1_BE",1177.no_pcm = 1,1178.capture_only = 1,1179SND_SOC_DAILINK_REG(UL_SRC1_BE),1180},1181[DAI_LINK_UL_SRC2_BE] = {1182.name = "UL_SRC2_BE",1183.no_pcm = 1,1184.capture_only = 1,1185SND_SOC_DAILINK_REG(UL_SRC2_BE),1186},1187/* SOF BE */1188[DAI_LINK_SOF_DL2_BE] = {1189.name = "AFE_SOF_DL2",1190.no_pcm = 1,1191.playback_only = 1,1192.ops = &mt8195_sof_be_ops,1193SND_SOC_DAILINK_REG(AFE_SOF_DL2),1194},1195[DAI_LINK_SOF_DL3_BE] = {1196.name = "AFE_SOF_DL3",1197.no_pcm = 1,1198.playback_only = 1,1199.ops = &mt8195_sof_be_ops,1200SND_SOC_DAILINK_REG(AFE_SOF_DL3),1201},1202[DAI_LINK_SOF_UL4_BE] = {1203.name = "AFE_SOF_UL4",1204.no_pcm = 1,1205.capture_only = 1,1206.ops = &mt8195_sof_be_ops,1207SND_SOC_DAILINK_REG(AFE_SOF_UL4),1208},1209[DAI_LINK_SOF_UL5_BE] = {1210.name = "AFE_SOF_UL5",1211.no_pcm = 1,1212.capture_only = 1,1213.ops = &mt8195_sof_be_ops,1214SND_SOC_DAILINK_REG(AFE_SOF_UL5),1215},1216};12171218static struct snd_soc_codec_conf rt1011_codec_conf[] = {1219{1220.dlc = COMP_CODEC_CONF(RT1011_DEV0_NAME),1221.name_prefix = "Left",1222},1223{1224.dlc = COMP_CODEC_CONF(RT1011_DEV1_NAME),1225.name_prefix = "Right",1226},1227};12281229static struct snd_soc_codec_conf max98390_codec_conf[] = {1230{1231.dlc = COMP_CODEC_CONF(MAX98390_DEV0_NAME),1232.name_prefix = "Right",1233},1234{1235.dlc = COMP_CODEC_CONF(MAX98390_DEV1_NAME),1236.name_prefix = "Left",1237},1238};12391240static struct snd_soc_card mt8195_mt6359_soc_card = {1241.owner = THIS_MODULE,1242.dai_link = mt8195_mt6359_dai_links,1243.num_links = ARRAY_SIZE(mt8195_mt6359_dai_links),1244.controls = mt8195_mt6359_controls,1245.num_controls = ARRAY_SIZE(mt8195_mt6359_controls),1246.dapm_widgets = mt8195_mt6359_widgets,1247.num_dapm_widgets = ARRAY_SIZE(mt8195_mt6359_widgets),1248.dapm_routes = mt8195_mt6359_routes,1249.num_dapm_routes = ARRAY_SIZE(mt8195_mt6359_routes),1250.set_bias_level_post = mt8195_set_bias_level_post,1251};12521253/* fixup the BE DAI link to match any values from topology */1254static int mt8195_dai_link_fixup(struct snd_soc_pcm_runtime *rtd,1255struct snd_pcm_hw_params *params)1256{1257int ret;12581259ret = mtk_sof_dai_link_fixup(rtd, params);12601261if (!strcmp(rtd->dai_link->name, "ETDM2_IN_BE") ||1262!strcmp(rtd->dai_link->name, "ETDM1_OUT_BE")) {1263mt8195_etdm_hw_params_fixup(rtd, params);1264}12651266return ret;1267}12681269static int mt8195_mt6359_legacy_probe(struct mtk_soc_card_data *soc_card_data)1270{1271struct mtk_platform_card_data *card_data = soc_card_data->card_data;1272struct snd_soc_card *card = card_data->card;1273struct device_node *codec_node, *dp_node, *hdmi_node;1274struct snd_soc_dai_link *dai_link;1275struct device *dev = card->dev;1276bool is5682s, init6359 = false;1277int i;12781279if (strstr(card->name, "_5682s")) {1280codec_node = of_find_compatible_node(NULL, NULL, "realtek,rt5682s");1281is5682s = true;1282} else {1283codec_node = of_find_compatible_node(NULL, NULL, "realtek,rt5682i");1284is5682s = false;1285}12861287dp_node = of_parse_phandle(dev->of_node, "mediatek,dptx-codec", 0);1288hdmi_node = of_parse_phandle(dev->of_node, "mediatek,hdmi-codec", 0);12891290for_each_card_prelinks(card, i, dai_link) {1291if (strcmp(dai_link->name, "DPTX_BE") == 0) {1292if (!dp_node) {1293dev_dbg(dev, "No property 'dptx-codec'\n");1294} else {1295dai_link->codecs->of_node = dp_node;1296dai_link->codecs->name = NULL;1297dai_link->codecs->dai_name = "i2s-hifi";1298dai_link->init = mt8195_dptx_codec_init;1299}1300} else if (strcmp(dai_link->name, "ETDM3_OUT_BE") == 0) {1301if (!hdmi_node) {1302dev_dbg(dev, "No property 'hdmi-codec'\n");1303} else {1304dai_link->codecs->of_node = hdmi_node;1305dai_link->codecs->name = NULL;1306dai_link->codecs->dai_name = "i2s-hifi";1307dai_link->init = mt8195_hdmi_codec_init;1308}1309} else if (strcmp(dai_link->name, "ETDM1_OUT_BE") == 0) {1310if (!codec_node) {1311dev_err(dev, "Codec not found!\n");1312} else {1313dai_link->codecs->of_node = codec_node;1314dai_link->codecs->name = NULL;1315dai_link->codecs->dai_name =1316is5682s ? RT5682S_CODEC_DAI : RT5682_CODEC_DAI;1317dai_link->init = mt8195_rt5682_init;1318dai_link->ops = &mt8195_rt5682_etdm_ops;1319}1320} else if (strcmp(dai_link->name, "ETDM2_IN_BE") == 0) {1321if (!codec_node) {1322dev_err(dev, "Codec not found!\n");1323} else {1324dai_link->codecs->of_node = codec_node;1325dai_link->codecs->name = NULL;1326dai_link->codecs->dai_name =1327is5682s ? RT5682S_CODEC_DAI : RT5682_CODEC_DAI;1328dai_link->ops = &mt8195_rt5682_etdm_ops;1329}1330} else if (strcmp(dai_link->name, "DL_SRC_BE") == 0 ||1331strcmp(dai_link->name, "UL_SRC1_BE") == 0 ||1332strcmp(dai_link->name, "UL_SRC2_BE") == 0) {1333if (!init6359) {1334dai_link->init = mt8195_mt6359_init;1335init6359 = true;1336}1337} else if (strcmp(dai_link->name, "ETDM2_OUT_BE") == 0) {1338switch (card_data->flags) {1339case RT1011_SPEAKER_AMP_PRESENT:1340dai_link->codecs = rt1011_comps;1341dai_link->num_codecs = ARRAY_SIZE(rt1011_comps);1342dai_link->init = mt8195_rt1011_init;1343dai_link->ops = &mt8195_rt1011_etdm_ops;1344dai_link->be_hw_params_fixup = mt8195_etdm_hw_params_fixup;1345card->codec_conf = rt1011_codec_conf;1346card->num_configs = ARRAY_SIZE(rt1011_codec_conf);1347break;1348case RT1019_SPEAKER_AMP_PRESENT:1349dai_link->codecs = rt1019_comps;1350dai_link->num_codecs = ARRAY_SIZE(rt1019_comps);1351dai_link->init = mt8195_rt1019_init;1352break;1353case MAX98390_SPEAKER_AMP_PRESENT:1354dai_link->codecs = max98390_comps;1355dai_link->num_codecs = ARRAY_SIZE(max98390_comps);1356dai_link->init = mt8195_max98390_init;1357card->codec_conf = max98390_codec_conf;1358card->num_configs = ARRAY_SIZE(max98390_codec_conf);1359break;1360default:1361break;1362}1363}1364}13651366return 0;1367}13681369static int mt8195_mt6359_soc_card_probe(struct mtk_soc_card_data *soc_card_data, bool legacy)1370{1371struct mtk_platform_card_data *card_data = soc_card_data->card_data;1372struct snd_soc_card *card = card_data->card;1373struct mt8195_mt6359_priv *mach_priv;1374struct snd_soc_dai_link *dai_link;1375u8 codec_init = 0;1376int i;13771378mach_priv = devm_kzalloc(card->dev, sizeof(*mach_priv), GFP_KERNEL);1379if (!mach_priv)1380return -ENOMEM;13811382soc_card_data->mach_priv = mach_priv;13831384if (legacy)1385return mt8195_mt6359_legacy_probe(soc_card_data);13861387for_each_card_prelinks(card, i, dai_link) {1388if (strcmp(dai_link->name, "DPTX_BE") == 0) {1389if (dai_link->num_codecs &&1390!snd_soc_dlc_is_dummy(dai_link->codecs))1391dai_link->init = mt8195_dptx_codec_init;1392} else if (strcmp(dai_link->name, "ETDM3_OUT_BE") == 0) {1393if (dai_link->num_codecs &&1394!snd_soc_dlc_is_dummy(dai_link->codecs))1395dai_link->init = mt8195_hdmi_codec_init;1396} else if (strcmp(dai_link->name, "DL_SRC_BE") == 0 ||1397strcmp(dai_link->name, "UL_SRC1_BE") == 0 ||1398strcmp(dai_link->name, "UL_SRC2_BE") == 0) {1399if (!(codec_init & MT6359_CODEC_INIT)) {1400dai_link->init = mt8195_mt6359_init;1401codec_init |= MT6359_CODEC_INIT;1402}1403} else if (strcmp(dai_link->name, "ETDM1_OUT_BE") == 0 ||1404strcmp(dai_link->name, "ETDM2_OUT_BE") == 0 ||1405strcmp(dai_link->name, "ETDM1_IN_BE") == 0 ||1406strcmp(dai_link->name, "ETDM2_IN_BE") == 0) {1407if (!dai_link->num_codecs)1408continue;14091410if (!strcmp(dai_link->codecs->dai_name, MAX98390_CODEC_DAI)) {1411if (!(codec_init & MAX98390_CODEC_INIT)) {1412dai_link->init = mt8195_max98390_init;1413codec_init |= MAX98390_CODEC_INIT;1414}1415} else if (!strcmp(dai_link->codecs->dai_name, RT1011_CODEC_DAI)) {1416dai_link->ops = &mt8195_rt1011_etdm_ops;1417if (!(codec_init & RT1011_CODEC_INIT)) {1418dai_link->init = mt8195_rt1011_init;1419codec_init |= RT1011_CODEC_INIT;1420}1421} else if (!strcmp(dai_link->codecs->dai_name, RT1019_CODEC_DAI)) {1422if (!(codec_init & RT1019_CODEC_INIT)) {1423dai_link->init = mt8195_rt1019_init;1424codec_init |= RT1019_CODEC_INIT;1425}1426} else if (!strcmp(dai_link->codecs->dai_name, RT5682_CODEC_DAI) ||1427!strcmp(dai_link->codecs->dai_name, RT5682S_CODEC_DAI)) {1428dai_link->ops = &mt8195_rt5682_etdm_ops;1429if (!(codec_init & RT5682_CODEC_INIT)) {1430dai_link->init = mt8195_rt5682_init;1431codec_init |= RT5682_CODEC_INIT;1432}1433} else {1434if (!snd_soc_dlc_is_dummy(dai_link->codecs)) {1435if (!(codec_init & DUMB_CODEC_INIT)) {1436dai_link->init = mt8195_dumb_amp_init;1437codec_init |= DUMB_CODEC_INIT;1438}1439}1440}1441}1442}14431444return 0;1445}14461447static const unsigned int mt8195_pcm_playback_channels[] = { 2 };1448static const unsigned int mt8195_pcm_capture_channels[] = { 1, 2 };1449static const unsigned int mt8195_pcm_hdmidp_channels[] = { 2, 4, 6, 8 };1450static const unsigned int mt8195_pcm_rates[] = { 48000 };14511452static const struct snd_pcm_hw_constraint_list mt8195_rate_constraint = {1453.list = mt8195_pcm_rates,1454.count = ARRAY_SIZE(mt8195_pcm_rates)1455};14561457static const struct mtk_pcm_constraints_data mt8195_pcm_constraints[MTK_CONSTRAINT_HDMIDP + 1] = {1458[MTK_CONSTRAINT_PLAYBACK] = {1459.channels = &(const struct snd_pcm_hw_constraint_list) {1460.list = mt8195_pcm_playback_channels,1461.count = ARRAY_SIZE(mt8195_pcm_playback_channels)1462},1463.rates = &mt8195_rate_constraint,1464},1465[MTK_CONSTRAINT_CAPTURE] = {1466.channels = &(const struct snd_pcm_hw_constraint_list) {1467.list = mt8195_pcm_capture_channels,1468.count = ARRAY_SIZE(mt8195_pcm_capture_channels)1469},1470.rates = &mt8195_rate_constraint,1471},1472[MTK_CONSTRAINT_HDMIDP] = {1473.channels = &(const struct snd_pcm_hw_constraint_list) {1474.list = mt8195_pcm_hdmidp_channels,1475.count = ARRAY_SIZE(mt8195_pcm_hdmidp_channels)1476},1477.rates = &mt8195_rate_constraint,1478},1479};14801481static const struct mtk_sof_priv mt8195_sof_priv = {1482.conn_streams = g_sof_conn_streams,1483.num_streams = ARRAY_SIZE(g_sof_conn_streams),1484.sof_dai_link_fixup = mt8195_dai_link_fixup1485};14861487static const struct mtk_soundcard_pdata mt8195_mt6359_rt1019_rt5682_card = {1488.card_name = "mt8195_r1019_5682",1489.card_data = &(struct mtk_platform_card_data) {1490.card = &mt8195_mt6359_soc_card,1491.num_jacks = MT8195_JACK_MAX,1492.pcm_constraints = mt8195_pcm_constraints,1493.num_pcm_constraints = ARRAY_SIZE(mt8195_pcm_constraints),1494.flags = RT1019_SPEAKER_AMP_PRESENT1495},1496.sof_priv = &mt8195_sof_priv,1497.soc_probe = mt8195_mt6359_soc_card_probe1498};14991500static const struct mtk_soundcard_pdata mt8195_mt6359_rt1011_rt5682_card = {1501.card_name = "mt8195_r1011_5682",1502.card_data = &(struct mtk_platform_card_data) {1503.card = &mt8195_mt6359_soc_card,1504.num_jacks = MT8195_JACK_MAX,1505.pcm_constraints = mt8195_pcm_constraints,1506.num_pcm_constraints = ARRAY_SIZE(mt8195_pcm_constraints),1507.flags = RT1011_SPEAKER_AMP_PRESENT1508},1509.sof_priv = &mt8195_sof_priv,1510.soc_probe = mt8195_mt6359_soc_card_probe1511};15121513static const struct mtk_soundcard_pdata mt8195_mt6359_max98390_rt5682_card = {1514.card_name = "mt8195_m98390_r5682",1515.card_data = &(struct mtk_platform_card_data) {1516.card = &mt8195_mt6359_soc_card,1517.num_jacks = MT8195_JACK_MAX,1518.pcm_constraints = mt8195_pcm_constraints,1519.num_pcm_constraints = ARRAY_SIZE(mt8195_pcm_constraints),1520.flags = MAX98390_SPEAKER_AMP_PRESENT1521},1522.sof_priv = &mt8195_sof_priv,1523.soc_probe = mt8195_mt6359_soc_card_probe1524};15251526static const struct mtk_soundcard_pdata mt8195_mt6359_card = {1527.card_name = "mt8195_mt6359",1528.card_data = &(struct mtk_platform_card_data) {1529.card = &mt8195_mt6359_soc_card,1530.num_jacks = MT8195_JACK_MAX,1531.pcm_constraints = mt8195_pcm_constraints,1532.num_pcm_constraints = ARRAY_SIZE(mt8195_pcm_constraints),1533},1534.sof_priv = &mt8195_sof_priv,1535.soc_probe = mt8195_mt6359_soc_card_probe1536};15371538static const struct of_device_id mt8195_mt6359_dt_match[] = {1539{1540.compatible = "mediatek,mt8195_mt6359_rt1019_rt5682",1541.data = &mt8195_mt6359_rt1019_rt5682_card,1542},1543{1544.compatible = "mediatek,mt8195_mt6359_rt1011_rt5682",1545.data = &mt8195_mt6359_rt1011_rt5682_card,1546},1547{1548.compatible = "mediatek,mt8195_mt6359_max98390_rt5682",1549.data = &mt8195_mt6359_max98390_rt5682_card,1550},1551{1552.compatible = "mediatek,mt8195_mt6359",1553.data = &mt8195_mt6359_card,1554},1555{},1556};1557MODULE_DEVICE_TABLE(of, mt8195_mt6359_dt_match);15581559static struct platform_driver mt8195_mt6359_driver = {1560.driver = {1561.name = "mt8195_mt6359",1562.of_match_table = mt8195_mt6359_dt_match,1563.pm = &snd_soc_pm_ops,1564},1565.probe = mtk_soundcard_common_probe,1566};15671568module_platform_driver(mt8195_mt6359_driver);15691570/* Module information */1571MODULE_DESCRIPTION("MT8195-MT6359 ALSA SoC machine driver");1572MODULE_AUTHOR("Trevor Wu <[email protected]>");1573MODULE_AUTHOR("YC Hung <[email protected]>");1574MODULE_LICENSE("GPL");1575MODULE_ALIAS("mt8195_mt6359 soc card");157615771578