Blame view
include/sound/soc-dai.h
12 KB
e2cfd2c96
|
1 2 |
/* SPDX-License-Identifier: GPL-2.0 * |
a47cbe726
|
3 4 5 6 |
* linux/sound/soc-dai.h -- ALSA SoC Layer * * Copyright: 2005-2008 Wolfson Microelectronics. PLC. * |
a47cbe726
|
7 8 9 10 11 12 13 14 |
* Digital Audio Interface (DAI) API. */ #ifndef __LINUX_SND_SOC_DAI_H #define __LINUX_SND_SOC_DAI_H #include <linux/list.h> |
d2e3cb85a
|
15 |
#include <sound/asoc.h> |
a47cbe726
|
16 17 |
struct snd_pcm_substream; |
888df395e
|
18 |
struct snd_soc_dapm_widget; |
496810778
|
19 |
struct snd_compr_stream; |
a47cbe726
|
20 21 22 23 24 25 26 |
/* * DAI hardware audio formats. * * Describes the physical PCM data formating and clocking. Add new formats * to the end. */ |
d2e3cb85a
|
27 28 29 30 31 32 33 |
#define SND_SOC_DAIFMT_I2S SND_SOC_DAI_FORMAT_I2S #define SND_SOC_DAIFMT_RIGHT_J SND_SOC_DAI_FORMAT_RIGHT_J #define SND_SOC_DAIFMT_LEFT_J SND_SOC_DAI_FORMAT_LEFT_J #define SND_SOC_DAIFMT_DSP_A SND_SOC_DAI_FORMAT_DSP_A #define SND_SOC_DAIFMT_DSP_B SND_SOC_DAI_FORMAT_DSP_B #define SND_SOC_DAIFMT_AC97 SND_SOC_DAI_FORMAT_AC97 #define SND_SOC_DAIFMT_PDM SND_SOC_DAI_FORMAT_PDM |
a47cbe726
|
34 35 36 37 38 39 40 41 |
/* left and right justified also known as MSB and LSB respectively */ #define SND_SOC_DAIFMT_MSB SND_SOC_DAIFMT_LEFT_J #define SND_SOC_DAIFMT_LSB SND_SOC_DAIFMT_RIGHT_J /* * DAI Clock gating. * |
47db8e89a
|
42 |
* DAI bit clocks can be be gated (disabled) when the DAI is not |
a47cbe726
|
43 44 |
* sending or receiving PCM data in a frame. This can be used to save power. */ |
75d9ac46b
|
45 |
#define SND_SOC_DAIFMT_CONT (1 << 4) /* continuous clock */ |
eef28e108
|
46 |
#define SND_SOC_DAIFMT_GATED (0 << 4) /* clock is gated */ |
a47cbe726
|
47 48 |
/* |
1d387a3fd
|
49 |
* DAI hardware signal polarity. |
a47cbe726
|
50 51 52 |
* * Specifies whether the DAI can also support inverted clocks for the specified * format. |
1d387a3fd
|
53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 |
* * BCLK: * - "normal" polarity means signal is available at rising edge of BCLK * - "inverted" polarity means signal is available at falling edge of BCLK * * FSYNC "normal" polarity depends on the frame format: * - I2S: frame consists of left then right channel data. Left channel starts * with falling FSYNC edge, right channel starts with rising FSYNC edge. * - Left/Right Justified: frame consists of left then right channel data. * Left channel starts with rising FSYNC edge, right channel starts with * falling FSYNC edge. * - DSP A/B: Frame starts with rising FSYNC edge. * - AC97: Frame starts with rising FSYNC edge. * * "Negative" FSYNC polarity is the one opposite of "normal" polarity. |
a47cbe726
|
68 |
*/ |
5d163336a
|
69 |
#define SND_SOC_DAIFMT_NB_NF (0 << 8) /* normal bit clock + frame */ |
75d9ac46b
|
70 71 72 |
#define SND_SOC_DAIFMT_NB_IF (2 << 8) /* normal BCLK + inv FRM */ #define SND_SOC_DAIFMT_IB_NF (3 << 8) /* invert BCLK + nor FRM */ #define SND_SOC_DAIFMT_IB_IF (4 << 8) /* invert BCLK + FRM */ |
a47cbe726
|
73 74 75 76 77 |
/* * DAI hardware clock masters. * * This is wrt the codec, the inverse is true for the interface |
47db8e89a
|
78 |
* i.e. if the codec is clk and FRM master then the interface is |
a47cbe726
|
79 80 |
* clk and frame slave. */ |
75d9ac46b
|
81 82 83 84 |
#define SND_SOC_DAIFMT_CBM_CFM (1 << 12) /* codec clk & FRM master */ #define SND_SOC_DAIFMT_CBS_CFM (2 << 12) /* codec clk slave & FRM master */ #define SND_SOC_DAIFMT_CBM_CFS (3 << 12) /* codec clk master & frame slave */ #define SND_SOC_DAIFMT_CBS_CFS (4 << 12) /* codec clk & FRM slave */ |
a47cbe726
|
85 86 87 88 89 90 91 92 93 94 95 |
#define SND_SOC_DAIFMT_FORMAT_MASK 0x000f #define SND_SOC_DAIFMT_CLOCK_MASK 0x00f0 #define SND_SOC_DAIFMT_INV_MASK 0x0f00 #define SND_SOC_DAIFMT_MASTER_MASK 0xf000 /* * Master Clock Directions */ #define SND_SOC_CLOCK_IN 0 #define SND_SOC_CLOCK_OUT 1 |
8f738d584
|
96 97 98 99 100 |
#define SND_SOC_STD_AC97_FMTS (SNDRV_PCM_FMTBIT_S8 |\ SNDRV_PCM_FMTBIT_S16_LE |\ SNDRV_PCM_FMTBIT_S16_BE |\ SNDRV_PCM_FMTBIT_S20_3LE |\ SNDRV_PCM_FMTBIT_S20_3BE |\ |
823dbb6eb
|
101 102 |
SNDRV_PCM_FMTBIT_S20_LE |\ SNDRV_PCM_FMTBIT_S20_BE |\ |
8f738d584
|
103 104 |
SNDRV_PCM_FMTBIT_S24_3LE |\ SNDRV_PCM_FMTBIT_S24_3BE |\ |
d34c43078
|
105 106 |
SNDRV_PCM_FMTBIT_S32_LE |\ SNDRV_PCM_FMTBIT_S32_BE) |
33f503c96
|
107 |
|
f0fba2ad1
|
108 |
struct snd_soc_dai_driver; |
a47cbe726
|
109 110 111 112 113 114 115 116 117 118 119 |
struct snd_soc_dai; struct snd_ac97_bus_ops; /* Digital Audio Interface clocking API.*/ int snd_soc_dai_set_sysclk(struct snd_soc_dai *dai, int clk_id, unsigned int freq, int dir); int snd_soc_dai_set_clkdiv(struct snd_soc_dai *dai, int div_id, int div); int snd_soc_dai_set_pll(struct snd_soc_dai *dai, |
85488037b
|
120 |
int pll_id, int source, unsigned int freq_in, unsigned int freq_out); |
a47cbe726
|
121 |
|
e54cf76ba
|
122 |
int snd_soc_dai_set_bclk_ratio(struct snd_soc_dai *dai, unsigned int ratio); |
a47cbe726
|
123 124 125 126 |
/* Digital Audio interface formatting */ int snd_soc_dai_set_fmt(struct snd_soc_dai *dai, unsigned int fmt); int snd_soc_dai_set_tdm_slot(struct snd_soc_dai *dai, |
a5479e389
|
127 |
unsigned int tx_mask, unsigned int rx_mask, int slots, int slot_width); |
a47cbe726
|
128 |
|
472df3cba
|
129 130 131 |
int snd_soc_dai_set_channel_map(struct snd_soc_dai *dai, unsigned int tx_num, unsigned int *tx_slot, unsigned int rx_num, unsigned int *rx_slot); |
a47cbe726
|
132 133 134 |
int snd_soc_dai_set_tristate(struct snd_soc_dai *dai, int tristate); /* Digital Audio Interface mute */ |
da18396f9
|
135 136 |
int snd_soc_dai_digital_mute(struct snd_soc_dai *dai, int mute, int direction); |
a47cbe726
|
137 |
|
467b061f1
|
138 139 140 141 |
int snd_soc_dai_get_channel_map(struct snd_soc_dai *dai, unsigned int *tx_num, unsigned int *tx_slot, unsigned int *rx_num, unsigned int *rx_slot); |
bece9e957
|
142 |
int snd_soc_dai_is_dummy(struct snd_soc_dai *dai); |
a47cbe726
|
143 144 145 146 147 148 149 |
struct snd_soc_dai_ops { /* * DAI clocking configuration, all optional. * Called by soc_card drivers, normally in their hw_params. */ int (*set_sysclk)(struct snd_soc_dai *dai, int clk_id, unsigned int freq, int dir); |
85488037b
|
150 151 |
int (*set_pll)(struct snd_soc_dai *dai, int pll_id, int source, unsigned int freq_in, unsigned int freq_out); |
a47cbe726
|
152 |
int (*set_clkdiv)(struct snd_soc_dai *dai, int div_id, int div); |
e54cf76ba
|
153 |
int (*set_bclk_ratio)(struct snd_soc_dai *dai, unsigned int ratio); |
a47cbe726
|
154 155 156 157 158 159 |
/* * DAI format configuration * Called by soc_card drivers, normally in their hw_params. */ int (*set_fmt)(struct snd_soc_dai *dai, unsigned int fmt); |
e5c215148
|
160 |
int (*xlate_tdm_slot_mask)(unsigned int slots, |
89c678571
|
161 |
unsigned int *tx_mask, unsigned int *rx_mask); |
a47cbe726
|
162 |
int (*set_tdm_slot)(struct snd_soc_dai *dai, |
a5479e389
|
163 164 |
unsigned int tx_mask, unsigned int rx_mask, int slots, int slot_width); |
472df3cba
|
165 166 167 |
int (*set_channel_map)(struct snd_soc_dai *dai, unsigned int tx_num, unsigned int *tx_slot, unsigned int rx_num, unsigned int *rx_slot); |
467b061f1
|
168 169 170 |
int (*get_channel_map)(struct snd_soc_dai *dai, unsigned int *tx_num, unsigned int *tx_slot, unsigned int *rx_num, unsigned int *rx_slot); |
a47cbe726
|
171 |
int (*set_tristate)(struct snd_soc_dai *dai, int tristate); |
97349b605
|
172 173 |
int (*set_sdw_stream)(struct snd_soc_dai *dai, void *stream, int direction); |
a47cbe726
|
174 175 176 177 178 |
/* * DAI digital mute - optional. * Called by soc-core to minimise any pops. */ int (*digital_mute)(struct snd_soc_dai *dai, int mute); |
da18396f9
|
179 |
int (*mute_stream)(struct snd_soc_dai *dai, int mute, int stream); |
dee89c4d9
|
180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 |
/* * ALSA PCM audio operations - all optional. * Called by soc-core during audio PCM operations. */ int (*startup)(struct snd_pcm_substream *, struct snd_soc_dai *); void (*shutdown)(struct snd_pcm_substream *, struct snd_soc_dai *); int (*hw_params)(struct snd_pcm_substream *, struct snd_pcm_hw_params *, struct snd_soc_dai *); int (*hw_free)(struct snd_pcm_substream *, struct snd_soc_dai *); int (*prepare)(struct snd_pcm_substream *, struct snd_soc_dai *); |
9f1614aae
|
195 196 197 198 199 200 201 |
/* * NOTE: Commands passed to the trigger function are not necessarily * compatible with the current state of the dai. For example this * sequence of commands is possible: START STOP STOP. * So do not unconditionally use refcounting functions in the trigger * function, e.g. clk_enable/disable. */ |
dee89c4d9
|
202 203 |
int (*trigger)(struct snd_pcm_substream *, int, struct snd_soc_dai *); |
07bf84aaf
|
204 205 |
int (*bespoke_trigger)(struct snd_pcm_substream *, int, struct snd_soc_dai *); |
258020d08
|
206 207 208 209 210 211 |
/* * For hardware based FIFO caused delay reporting. * Optional. */ snd_pcm_sframes_t (*delay)(struct snd_pcm_substream *, struct snd_soc_dai *); |
a47cbe726
|
212 |
}; |
2e622ae41
|
213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 |
struct snd_soc_cdai_ops { /* * for compress ops */ int (*startup)(struct snd_compr_stream *, struct snd_soc_dai *); int (*shutdown)(struct snd_compr_stream *, struct snd_soc_dai *); int (*set_params)(struct snd_compr_stream *, struct snd_compr_params *, struct snd_soc_dai *); int (*get_params)(struct snd_compr_stream *, struct snd_codec *, struct snd_soc_dai *); int (*set_metadata)(struct snd_compr_stream *, struct snd_compr_metadata *, struct snd_soc_dai *); int (*get_metadata)(struct snd_compr_stream *, struct snd_compr_metadata *, struct snd_soc_dai *); int (*trigger)(struct snd_compr_stream *, int, struct snd_soc_dai *); int (*pointer)(struct snd_compr_stream *, struct snd_compr_tstamp *, struct snd_soc_dai *); int (*ack)(struct snd_compr_stream *, size_t, struct snd_soc_dai *); }; |
a47cbe726
|
236 |
/* |
f0fba2ad1
|
237 |
* Digital Audio Interface Driver. |
a47cbe726
|
238 |
* |
f0fba2ad1
|
239 240 241 242 243 244 |
* Describes the Digital Audio Interface in terms of its ALSA, DAI and AC97 * operations and capabilities. Codec and platform drivers will register this * structure for every DAI they have. * * This structure covers the clocking, formating and ALSA operations for each * interface. |
a47cbe726
|
245 |
*/ |
f0fba2ad1
|
246 |
struct snd_soc_dai_driver { |
a47cbe726
|
247 |
/* DAI description */ |
f0fba2ad1
|
248 |
const char *name; |
a47cbe726
|
249 |
unsigned int id; |
623682941
|
250 |
unsigned int base; |
68003e6cf
|
251 |
struct snd_soc_dobj dobj; |
a47cbe726
|
252 |
|
f0fba2ad1
|
253 254 255 |
/* DAI driver callbacks */ int (*probe)(struct snd_soc_dai *dai); int (*remove)(struct snd_soc_dai *dai); |
dc7d7b830
|
256 257 |
int (*suspend)(struct snd_soc_dai *dai); int (*resume)(struct snd_soc_dai *dai); |
496810778
|
258 |
/* compress dai */ |
6f0c42269
|
259 |
int (*compress_new)(struct snd_soc_pcm_runtime *rtd, int num); |
25f7b701c
|
260 261 262 |
/* Optional Callback used at pcm creation*/ int (*pcm_new)(struct snd_soc_pcm_runtime *rtd, struct snd_soc_dai *dai); |
bc2632140
|
263 264 |
/* DAI is also used for the control bus */ bool bus_control; |
a47cbe726
|
265 266 |
/* ops */ |
1ee46ebd0
|
267 |
const struct snd_soc_dai_ops *ops; |
2e622ae41
|
268 |
const struct snd_soc_cdai_ops *cops; |
a47cbe726
|
269 270 271 272 |
/* DAI capabilities */ struct snd_soc_pcm_stream capture; struct snd_soc_pcm_stream playback; |
06f409d76
|
273 |
unsigned int symmetric_rates:1; |
3635bf09a
|
274 275 |
unsigned int symmetric_channels:1; unsigned int symmetric_samplebits:1; |
0168bf0d1
|
276 277 278 279 |
/* probe ordering - for components with runtime dependencies */ int probe_order; int remove_order; |
f0fba2ad1
|
280 281 282 283 284 285 286 287 288 289 290 |
}; /* * Digital Audio Interface runtime data. * * Holds runtime data for a DAI. */ struct snd_soc_dai { const char *name; int id; struct device *dev; |
f0fba2ad1
|
291 292 293 |
/* driver ops */ struct snd_soc_dai_driver *driver; |
a47cbe726
|
294 295 |
/* DAI runtime info */ |
40c579637
|
296 297 |
unsigned int capture_active; /* stream usage count */ unsigned int playback_active; /* stream usage count */ |
39b2238e2
|
298 |
unsigned int probed:1; |
a47cbe726
|
299 |
unsigned int active; |
a47cbe726
|
300 |
|
888df395e
|
301 302 |
struct snd_soc_dapm_widget *playback_widget; struct snd_soc_dapm_widget *capture_widget; |
f0fba2ad1
|
303 304 305 |
/* DAI DMA data */ void *playback_dma_data; void *capture_dma_data; |
a47cbe726
|
306 |
|
17841020e
|
307 308 |
/* Symmetry data - only valid if symmetry is being enforced */ unsigned int rate; |
3635bf09a
|
309 310 |
unsigned int channels; unsigned int sample_bits; |
17841020e
|
311 |
|
f0fba2ad1
|
312 |
/* parent platform/codec */ |
6106d1294
|
313 |
struct snd_soc_component *component; |
2466ab970
|
314 |
|
88bd870f0
|
315 316 317 |
/* CODEC TDM slot masks and params (for fixup) */ unsigned int tx_mask; unsigned int rx_mask; |
a47cbe726
|
318 319 |
struct list_head list; }; |
fd23b7dee
|
320 321 322 323 |
static inline void *snd_soc_dai_get_dma_data(const struct snd_soc_dai *dai, const struct snd_pcm_substream *ss) { return (ss->stream == SNDRV_PCM_STREAM_PLAYBACK) ? |
f0fba2ad1
|
324 |
dai->playback_dma_data : dai->capture_dma_data; |
fd23b7dee
|
325 326 327 328 329 330 331 |
} static inline void snd_soc_dai_set_dma_data(struct snd_soc_dai *dai, const struct snd_pcm_substream *ss, void *data) { if (ss->stream == SNDRV_PCM_STREAM_PLAYBACK) |
f0fba2ad1
|
332 |
dai->playback_dma_data = data; |
fd23b7dee
|
333 |
else |
f0fba2ad1
|
334 335 |
dai->capture_dma_data = data; } |
ecfc0c04f
|
336 337 338 339 340 341 |
static inline void snd_soc_dai_init_dma_data(struct snd_soc_dai *dai, void *playback, void *capture) { dai->playback_dma_data = playback; dai->capture_dma_data = capture; } |
f0fba2ad1
|
342 343 344 345 346 347 348 349 350 |
static inline void snd_soc_dai_set_drvdata(struct snd_soc_dai *dai, void *data) { dev_set_drvdata(dai->dev, data); } static inline void *snd_soc_dai_get_drvdata(struct snd_soc_dai *dai) { return dev_get_drvdata(dai->dev); |
fd23b7dee
|
351 |
} |
97349b605
|
352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 |
/** * snd_soc_dai_set_sdw_stream() - Configures a DAI for SDW stream operation * @dai: DAI * @stream: STREAM * @direction: Stream direction(Playback/Capture) * SoundWire subsystem doesn't have a notion of direction and we reuse * the ASoC stream direction to configure sink/source ports. * Playback maps to source ports and Capture for sink ports. * * This should be invoked with NULL to clear the stream set previously. * Returns 0 on success, a negative error code otherwise. */ static inline int snd_soc_dai_set_sdw_stream(struct snd_soc_dai *dai, void *stream, int direction) { if (dai->driver->ops->set_sdw_stream) return dai->driver->ops->set_sdw_stream(dai, stream, direction); else return -ENOTSUPP; } |
a47cbe726
|
372 |
#endif |