1 /* SPDX-License-Identifier: GPL-2.0-only */ 2 /* 3 * This file incorporates work covered by the following copyright notice: 4 * Copyright (c) 2020 Intel Corporation 5 * Copyright(c) 2024 Advanced Micro Devices, Inc. 6 * 7 */ 8 9 #ifndef SOC_SDW_UTILS_H 10 #define SOC_SDW_UTILS_H 11 12 #include <sound/soc.h> 13 #include <sound/soc-acpi.h> 14 15 #define SOC_SDW_MAX_DAI_NUM 8 16 #define SOC_SDW_MAX_NO_PROPS 2 17 #define SOC_SDW_JACK_JDSRC(quirk) ((quirk) & GENMASK(3, 0)) 18 19 /* If a CODEC has an optional speaker output, this quirk will enable it */ 20 #define SOC_SDW_CODEC_SPKR BIT(15) 21 /* 22 * If the CODEC has additional devices attached directly to it. 23 * 24 * For the cs42l43: 25 * - 0 - No speaker output 26 * - SOC_SDW_CODEC_SPKR - CODEC internal speaker 27 * - SOC_SDW_SIDECAR_AMPS - 2x Sidecar amplifiers + CODEC internal speaker 28 * - SOC_SDW_CODEC_SPKR | SOF_SIDECAR_AMPS - Not currently supported 29 */ 30 #define SOC_SDW_SIDECAR_AMPS BIT(16) 31 32 #define SOC_SDW_UNUSED_DAI_ID -1 33 #define SOC_SDW_JACK_OUT_DAI_ID 0 34 #define SOC_SDW_JACK_IN_DAI_ID 1 35 #define SOC_SDW_AMP_OUT_DAI_ID 2 36 #define SOC_SDW_AMP_IN_DAI_ID 3 37 #define SOC_SDW_DMIC_DAI_ID 4 38 39 #define SOC_SDW_DAI_TYPE_JACK 0 40 #define SOC_SDW_DAI_TYPE_AMP 1 41 #define SOC_SDW_DAI_TYPE_MIC 2 42 43 struct asoc_sdw_codec_info; 44 45 struct asoc_sdw_dai_info { 46 const bool direction[2]; /* playback & capture support */ 47 const char *dai_name; 48 const int dai_type; 49 const int dailink[2]; /* dailink id for each direction */ 50 const struct snd_kcontrol_new *controls; 51 const int num_controls; 52 const struct snd_soc_dapm_widget *widgets; 53 const int num_widgets; 54 int (*init)(struct snd_soc_card *card, 55 struct snd_soc_dai_link *dai_links, 56 struct asoc_sdw_codec_info *info, 57 bool playback); 58 int (*exit)(struct snd_soc_card *card, struct snd_soc_dai_link *dai_link); 59 int (*rtd_init)(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 60 bool rtd_init_done; /* Indicate that the rtd_init callback is done */ 61 unsigned long quirk; 62 }; 63 64 struct asoc_sdw_codec_info { 65 const int part_id; 66 const int version_id; 67 const char *codec_name; 68 int amp_num; 69 const u8 acpi_id[ACPI_ID_LEN]; 70 const bool ignore_internal_dmic; 71 const struct snd_soc_ops *ops; 72 struct asoc_sdw_dai_info dais[SOC_SDW_MAX_DAI_NUM]; 73 const int dai_num; 74 75 int (*codec_card_late_probe)(struct snd_soc_card *card); 76 77 int (*count_sidecar)(struct snd_soc_card *card, 78 int *num_dais, int *num_devs); 79 int (*add_sidecar)(struct snd_soc_card *card, 80 struct snd_soc_dai_link **dai_links, 81 struct snd_soc_codec_conf **codec_conf); 82 }; 83 84 struct asoc_sdw_mc_private { 85 struct snd_soc_card card; 86 struct snd_soc_jack sdw_headset; 87 struct device *headset_codec_dev; /* only one headset per card */ 88 struct device *amp_dev1, *amp_dev2; 89 bool append_dai_type; 90 bool ignore_internal_dmic; 91 void *private; 92 unsigned long mc_quirk; 93 int codec_info_list_count; 94 }; 95 96 extern struct asoc_sdw_codec_info codec_info_list[]; 97 int asoc_sdw_get_codec_info_list_count(void); 98 99 int asoc_sdw_startup(struct snd_pcm_substream *substream); 100 int asoc_sdw_prepare(struct snd_pcm_substream *substream); 101 int asoc_sdw_prepare(struct snd_pcm_substream *substream); 102 int asoc_sdw_trigger(struct snd_pcm_substream *substream, int cmd); 103 int asoc_sdw_hw_params(struct snd_pcm_substream *substream, 104 struct snd_pcm_hw_params *params); 105 int asoc_sdw_hw_free(struct snd_pcm_substream *substream); 106 void asoc_sdw_shutdown(struct snd_pcm_substream *substream); 107 108 const char *asoc_sdw_get_codec_name(struct device *dev, 109 const struct asoc_sdw_codec_info *codec_info, 110 const struct snd_soc_acpi_link_adr *adr_link, 111 int adr_index); 112 113 struct asoc_sdw_codec_info *asoc_sdw_find_codec_info_part(const u64 adr); 114 115 struct asoc_sdw_codec_info *asoc_sdw_find_codec_info_acpi(const u8 *acpi_id); 116 117 struct asoc_sdw_codec_info *asoc_sdw_find_codec_info_dai(const char *dai_name, 118 int *dai_index); 119 120 struct snd_soc_dai_link *asoc_sdw_mc_find_codec_dai_used(struct snd_soc_card *card, 121 const char *dai_name); 122 123 void asoc_sdw_mc_dailink_exit_loop(struct snd_soc_card *card); 124 125 int asoc_sdw_card_late_probe(struct snd_soc_card *card); 126 127 void asoc_sdw_init_dai_link(struct device *dev, struct snd_soc_dai_link *dai_links, 128 int *be_id, char *name, int playback, int capture, 129 struct snd_soc_dai_link_component *cpus, int cpus_num, 130 struct snd_soc_dai_link_component *platform_component, 131 int num_platforms, struct snd_soc_dai_link_component *codecs, 132 int codecs_num, int (*init)(struct snd_soc_pcm_runtime *rtd), 133 const struct snd_soc_ops *ops); 134 135 int asoc_sdw_init_simple_dai_link(struct device *dev, struct snd_soc_dai_link *dai_links, 136 int *be_id, char *name, int playback, int capture, 137 const char *cpu_dai_name, const char *platform_comp_name, 138 int num_platforms, const char *codec_name, 139 const char *codec_dai_name, 140 int (*init)(struct snd_soc_pcm_runtime *rtd), 141 const struct snd_soc_ops *ops); 142 143 int asoc_sdw_rtd_init(struct snd_soc_pcm_runtime *rtd); 144 145 /* DMIC support */ 146 int asoc_sdw_dmic_init(struct snd_soc_pcm_runtime *rtd); 147 148 /* RT711 support */ 149 int asoc_sdw_rt711_init(struct snd_soc_card *card, 150 struct snd_soc_dai_link *dai_links, 151 struct asoc_sdw_codec_info *info, 152 bool playback); 153 int asoc_sdw_rt711_exit(struct snd_soc_card *card, struct snd_soc_dai_link *dai_link); 154 155 /* RT711-SDCA support */ 156 int asoc_sdw_rt_sdca_jack_init(struct snd_soc_card *card, 157 struct snd_soc_dai_link *dai_links, 158 struct asoc_sdw_codec_info *info, 159 bool playback); 160 int asoc_sdw_rt_sdca_jack_exit(struct snd_soc_card *card, struct snd_soc_dai_link *dai_link); 161 162 /* RT1308 I2S support */ 163 extern const struct snd_soc_ops soc_sdw_rt1308_i2s_ops; 164 165 /* generic amp support */ 166 int asoc_sdw_rt_amp_init(struct snd_soc_card *card, 167 struct snd_soc_dai_link *dai_links, 168 struct asoc_sdw_codec_info *info, 169 bool playback); 170 int asoc_sdw_rt_amp_exit(struct snd_soc_card *card, struct snd_soc_dai_link *dai_link); 171 172 /* CS42L43 support */ 173 int asoc_sdw_cs42l43_spk_init(struct snd_soc_card *card, 174 struct snd_soc_dai_link *dai_links, 175 struct asoc_sdw_codec_info *info, 176 bool playback); 177 178 /* CS AMP support */ 179 int asoc_sdw_bridge_cs35l56_count_sidecar(struct snd_soc_card *card, 180 int *num_dais, int *num_devs); 181 int asoc_sdw_bridge_cs35l56_add_sidecar(struct snd_soc_card *card, 182 struct snd_soc_dai_link **dai_links, 183 struct snd_soc_codec_conf **codec_conf); 184 int asoc_sdw_bridge_cs35l56_spk_init(struct snd_soc_card *card, 185 struct snd_soc_dai_link *dai_links, 186 struct asoc_sdw_codec_info *info, 187 bool playback); 188 189 int asoc_sdw_cs_amp_init(struct snd_soc_card *card, 190 struct snd_soc_dai_link *dai_links, 191 struct asoc_sdw_codec_info *info, 192 bool playback); 193 194 /* MAXIM codec support */ 195 int asoc_sdw_maxim_init(struct snd_soc_card *card, 196 struct snd_soc_dai_link *dai_links, 197 struct asoc_sdw_codec_info *info, 198 bool playback); 199 200 /* dai_link init callbacks */ 201 int asoc_sdw_rt_dmic_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 202 int asoc_sdw_rt_sdca_jack_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 203 int asoc_sdw_rt_amp_spk_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 204 int asoc_sdw_rt700_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 205 int asoc_sdw_rt711_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 206 int asoc_sdw_rt712_spk_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 207 int asoc_sdw_rt722_spk_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 208 int asoc_sdw_rt5682_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 209 int asoc_sdw_cs42l42_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 210 int asoc_sdw_cs42l43_hs_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 211 int asoc_sdw_cs42l43_spk_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 212 int asoc_sdw_cs42l43_dmic_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 213 int asoc_sdw_cs_spk_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 214 int asoc_sdw_maxim_spk_rtd_init(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); 215 216 #endif 217