blob: 82a1430313dccdfc73a14b593aa4b176928a77f7 [file] [log] [blame]
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +09001// SPDX-License-Identifier: GPL-2.0
2//
3// soc-component.c
4//
Kuninori Morimoto460b42d2020-06-04 17:08:03 +09005// Copyright 2009-2011 Wolfson Microelectronics PLC.
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +09006// Copyright (C) 2019 Renesas Electronics Corp.
Kuninori Morimoto460b42d2020-06-04 17:08:03 +09007//
8// Mark Brown <broonie@opensource.wolfsonmicro.com>
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +09009// Kuninori Morimoto <kuninori.morimoto.gx@renesas.com>
10//
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +090011#include <linux/module.h>
Kuninori Morimoto939a5cf2020-09-28 09:01:17 +090012#include <linux/pm_runtime.h>
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +090013#include <sound/soc.h>
Srinivas Kandagatla8ac9e472021-01-29 10:05:39 +000014#include <linux/bitops.h>
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +090015
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +090016#define soc_component_ret(dai, ret) _soc_component_ret(dai, __func__, ret)
17static inline int _soc_component_ret(struct snd_soc_component *component,
18 const char *func, int ret)
19{
20 /* Positive/Zero values are not errors */
21 if (ret >= 0)
22 return ret;
23
24 /* Negative values might be errors */
25 switch (ret) {
26 case -EPROBE_DEFER:
27 case -ENOTSUPP:
28 break;
29 default:
30 dev_err(component->dev,
31 "ASoC: error at %s on %s: %d\n",
32 func, component->name, ret);
33 }
34
35 return ret;
36}
37
Srinivas Kandagatla1da0b982021-01-26 17:17:48 +000038static inline int soc_component_field_shift(struct snd_soc_component *component,
39 unsigned int mask)
40{
41 if (!mask) {
42 dev_err(component->dev, "ASoC: error field mask is zero for %s\n",
43 component->name);
44 return 0;
45 }
46
Srinivas Kandagatla8ac9e472021-01-29 10:05:39 +000047 return (ffs(mask) - 1);
Srinivas Kandagatla1da0b982021-01-26 17:17:48 +000048}
49
Kuninori Morimoto51aff912020-09-28 09:01:04 +090050/*
51 * We might want to check substream by using list.
52 * In such case, we can update these macros.
53 */
54#define soc_component_mark_push(component, substream, tgt) ((component)->mark_##tgt = substream)
55#define soc_component_mark_pop(component, substream, tgt) ((component)->mark_##tgt = NULL)
56#define soc_component_mark_match(component, substream, tgt) ((component)->mark_##tgt == substream)
57
Kuninori Morimoto257c4da2020-06-04 17:07:54 +090058void snd_soc_component_set_aux(struct snd_soc_component *component,
59 struct snd_soc_aux_dev *aux)
60{
61 component->init = (aux) ? aux->init : NULL;
62}
63
64int snd_soc_component_init(struct snd_soc_component *component)
65{
66 int ret = 0;
67
68 if (component->init)
69 ret = component->init(component);
70
71 return soc_component_ret(component, ret);
72}
73
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +090074/**
75 * snd_soc_component_set_sysclk - configure COMPONENT system or master clock.
76 * @component: COMPONENT
77 * @clk_id: DAI specific clock ID
78 * @source: Source for the clock
79 * @freq: new clock frequency in Hz
80 * @dir: new clock direction - input/output.
81 *
82 * Configures the CODEC master (MCLK) or system (SYSCLK) clocking.
83 */
84int snd_soc_component_set_sysclk(struct snd_soc_component *component,
85 int clk_id, int source, unsigned int freq,
86 int dir)
87{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +090088 int ret = -ENOTSUPP;
89
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +090090 if (component->driver->set_sysclk)
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +090091 ret = component->driver->set_sysclk(component, clk_id, source,
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +090092 freq, dir);
93
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +090094 return soc_component_ret(component, ret);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +090095}
96EXPORT_SYMBOL_GPL(snd_soc_component_set_sysclk);
97
98/*
99 * snd_soc_component_set_pll - configure component PLL.
100 * @component: COMPONENT
101 * @pll_id: DAI specific PLL ID
102 * @source: DAI specific source for the PLL
103 * @freq_in: PLL input clock frequency in Hz
104 * @freq_out: requested PLL output clock frequency in Hz
105 *
106 * Configures and enables PLL to generate output clock based on input clock.
107 */
108int snd_soc_component_set_pll(struct snd_soc_component *component, int pll_id,
109 int source, unsigned int freq_in,
110 unsigned int freq_out)
111{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900112 int ret = -EINVAL;
113
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900114 if (component->driver->set_pll)
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900115 ret = component->driver->set_pll(component, pll_id, source,
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900116 freq_in, freq_out);
117
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900118 return soc_component_ret(component, ret);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900119}
120EXPORT_SYMBOL_GPL(snd_soc_component_set_pll);
121
Kuninori Morimoto9d415fb2019-07-26 13:51:35 +0900122void snd_soc_component_seq_notifier(struct snd_soc_component *component,
123 enum snd_soc_dapm_type type, int subseq)
124{
125 if (component->driver->seq_notifier)
126 component->driver->seq_notifier(component, type, subseq);
127}
128
Kuninori Morimoto8e2a9902019-07-26 13:51:39 +0900129int snd_soc_component_stream_event(struct snd_soc_component *component,
130 int event)
131{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900132 int ret = 0;
Kuninori Morimoto8e2a9902019-07-26 13:51:39 +0900133
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900134 if (component->driver->stream_event)
135 ret = component->driver->stream_event(component, event);
136
137 return soc_component_ret(component, ret);
Kuninori Morimoto8e2a9902019-07-26 13:51:39 +0900138}
139
Kuninori Morimoto7951b1462019-07-26 13:51:43 +0900140int snd_soc_component_set_bias_level(struct snd_soc_component *component,
141 enum snd_soc_bias_level level)
142{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900143 int ret = 0;
Kuninori Morimoto7951b1462019-07-26 13:51:43 +0900144
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900145 if (component->driver->set_bias_level)
146 ret = component->driver->set_bias_level(component, level);
147
148 return soc_component_ret(component, ret);
Kuninori Morimoto7951b1462019-07-26 13:51:43 +0900149}
150
Kuninori Morimoto4ca87012020-06-04 17:06:11 +0900151int snd_soc_component_enable_pin(struct snd_soc_component *component,
152 const char *pin)
153{
Mark Brown31428c72021-07-26 20:41:23 +0100154 struct snd_soc_dapm_context *dapm =
155 snd_soc_component_get_dapm(component);
156 return snd_soc_dapm_enable_pin(dapm, pin);
Kuninori Morimoto4ca87012020-06-04 17:06:11 +0900157}
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900158EXPORT_SYMBOL_GPL(snd_soc_component_enable_pin);
159
160int snd_soc_component_enable_pin_unlocked(struct snd_soc_component *component,
161 const char *pin)
162{
Mark Brown31428c72021-07-26 20:41:23 +0100163 struct snd_soc_dapm_context *dapm =
164 snd_soc_component_get_dapm(component);
165 return snd_soc_dapm_enable_pin_unlocked(dapm, pin);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900166}
167EXPORT_SYMBOL_GPL(snd_soc_component_enable_pin_unlocked);
168
169int snd_soc_component_disable_pin(struct snd_soc_component *component,
170 const char *pin)
171{
Mark Brown31428c72021-07-26 20:41:23 +0100172 struct snd_soc_dapm_context *dapm =
173 snd_soc_component_get_dapm(component);
174 return snd_soc_dapm_disable_pin(dapm, pin);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900175}
176EXPORT_SYMBOL_GPL(snd_soc_component_disable_pin);
177
178int snd_soc_component_disable_pin_unlocked(struct snd_soc_component *component,
179 const char *pin)
180{
Mark Brown31428c72021-07-26 20:41:23 +0100181 struct snd_soc_dapm_context *dapm =
182 snd_soc_component_get_dapm(component);
183 return snd_soc_dapm_disable_pin_unlocked(dapm, pin);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900184}
185EXPORT_SYMBOL_GPL(snd_soc_component_disable_pin_unlocked);
186
187int snd_soc_component_nc_pin(struct snd_soc_component *component,
188 const char *pin)
189{
Mark Brown31428c72021-07-26 20:41:23 +0100190 struct snd_soc_dapm_context *dapm =
191 snd_soc_component_get_dapm(component);
192 return snd_soc_dapm_nc_pin(dapm, pin);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900193}
194EXPORT_SYMBOL_GPL(snd_soc_component_nc_pin);
195
196int snd_soc_component_nc_pin_unlocked(struct snd_soc_component *component,
197 const char *pin)
198{
Mark Brown31428c72021-07-26 20:41:23 +0100199 struct snd_soc_dapm_context *dapm =
200 snd_soc_component_get_dapm(component);
201 return snd_soc_dapm_nc_pin_unlocked(dapm, pin);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900202}
203EXPORT_SYMBOL_GPL(snd_soc_component_nc_pin_unlocked);
204
205int snd_soc_component_get_pin_status(struct snd_soc_component *component,
206 const char *pin)
207{
Mark Brown31428c72021-07-26 20:41:23 +0100208 struct snd_soc_dapm_context *dapm =
209 snd_soc_component_get_dapm(component);
210 return snd_soc_dapm_get_pin_status(dapm, pin);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900211}
212EXPORT_SYMBOL_GPL(snd_soc_component_get_pin_status);
213
214int snd_soc_component_force_enable_pin(struct snd_soc_component *component,
215 const char *pin)
216{
Mark Brown31428c72021-07-26 20:41:23 +0100217 struct snd_soc_dapm_context *dapm =
218 snd_soc_component_get_dapm(component);
219 return snd_soc_dapm_force_enable_pin(dapm, pin);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900220}
221EXPORT_SYMBOL_GPL(snd_soc_component_force_enable_pin);
222
223int snd_soc_component_force_enable_pin_unlocked(
224 struct snd_soc_component *component,
225 const char *pin)
226{
Mark Brown31428c72021-07-26 20:41:23 +0100227 struct snd_soc_dapm_context *dapm =
228 snd_soc_component_get_dapm(component);
229 return snd_soc_dapm_force_enable_pin_unlocked(dapm, pin);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900230}
231EXPORT_SYMBOL_GPL(snd_soc_component_force_enable_pin_unlocked);
232
233/**
234 * snd_soc_component_set_jack - configure component jack.
235 * @component: COMPONENTs
236 * @jack: structure to use for the jack
237 * @data: can be used if codec driver need extra data for configuring jack
238 *
239 * Configures and enables jack detection function.
240 */
241int snd_soc_component_set_jack(struct snd_soc_component *component,
242 struct snd_soc_jack *jack, void *data)
243{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900244 int ret = -ENOTSUPP;
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900245
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900246 if (component->driver->set_jack)
247 ret = component->driver->set_jack(component, jack, data);
248
249 return soc_component_ret(component, ret);
Kuninori Morimoto4ff1fef2019-07-26 13:49:48 +0900250}
251EXPORT_SYMBOL_GPL(snd_soc_component_set_jack);
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +0900252
253int snd_soc_component_module_get(struct snd_soc_component *component,
Peter Ujfalusia739fdc2021-09-01 12:52:54 +0300254 void *mark, int upon_open)
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +0900255{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900256 int ret = 0;
257
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +0900258 if (component->driver->module_get_upon_open == !!upon_open &&
259 !try_module_get(component->dev->driver->owner))
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900260 ret = -ENODEV;
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +0900261
Peter Ujfalusia739fdc2021-09-01 12:52:54 +0300262 /* mark module if succeeded */
Kuninori Morimoto51aff912020-09-28 09:01:04 +0900263 if (ret == 0)
Peter Ujfalusia739fdc2021-09-01 12:52:54 +0300264 soc_component_mark_push(component, mark, module);
Kuninori Morimoto51aff912020-09-28 09:01:04 +0900265
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900266 return soc_component_ret(component, ret);
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +0900267}
268
269void snd_soc_component_module_put(struct snd_soc_component *component,
Peter Ujfalusia739fdc2021-09-01 12:52:54 +0300270 void *mark, int upon_open, int rollback)
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +0900271{
Peter Ujfalusia739fdc2021-09-01 12:52:54 +0300272 if (rollback && !soc_component_mark_match(component, mark, module))
Kuninori Morimoto51aff912020-09-28 09:01:04 +0900273 return;
274
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +0900275 if (component->driver->module_get_upon_open == !!upon_open)
276 module_put(component->dev->driver->owner);
Kuninori Morimoto51aff912020-09-28 09:01:04 +0900277
Peter Ujfalusia739fdc2021-09-01 12:52:54 +0300278 /* remove the mark from module */
279 soc_component_mark_pop(component, mark, module);
Kuninori Morimoto4a81e8f2019-07-26 13:49:54 +0900280}
Kuninori Morimotoae2f4842019-07-26 13:50:01 +0900281
282int snd_soc_component_open(struct snd_soc_component *component,
283 struct snd_pcm_substream *substream)
284{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900285 int ret = 0;
286
Kuninori Morimotoe2cb4a12019-10-02 14:30:48 +0900287 if (component->driver->open)
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900288 ret = component->driver->open(component, substream);
289
Kuninori Morimoto51aff912020-09-28 09:01:04 +0900290 /* mark substream if succeeded */
291 if (ret == 0)
292 soc_component_mark_push(component, substream, open);
293
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900294 return soc_component_ret(component, ret);
Kuninori Morimotoae2f4842019-07-26 13:50:01 +0900295}
Kuninori Morimoto3672beb2019-07-26 13:50:07 +0900296
297int snd_soc_component_close(struct snd_soc_component *component,
Kuninori Morimoto51aff912020-09-28 09:01:04 +0900298 struct snd_pcm_substream *substream,
299 int rollback)
Kuninori Morimoto3672beb2019-07-26 13:50:07 +0900300{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900301 int ret = 0;
302
Kuninori Morimoto51aff912020-09-28 09:01:04 +0900303 if (rollback && !soc_component_mark_match(component, substream, open))
304 return 0;
305
Kuninori Morimotoe2cb4a12019-10-02 14:30:48 +0900306 if (component->driver->close)
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900307 ret = component->driver->close(component, substream);
308
Kuninori Morimoto51aff912020-09-28 09:01:04 +0900309 /* remove marked substream */
310 soc_component_mark_pop(component, substream, open);
311
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900312 return soc_component_ret(component, ret);
Kuninori Morimoto3672beb2019-07-26 13:50:07 +0900313}
Kuninori Morimoto6d537232019-07-26 13:50:13 +0900314
Kuninori Morimoto66c51572019-07-26 13:50:34 +0900315void snd_soc_component_suspend(struct snd_soc_component *component)
316{
317 if (component->driver->suspend)
318 component->driver->suspend(component);
319 component->suspended = 1;
320}
Kuninori Morimoto9a840cb2019-07-26 13:51:08 +0900321
322void snd_soc_component_resume(struct snd_soc_component *component)
323{
324 if (component->driver->resume)
325 component->driver->resume(component);
326 component->suspended = 0;
327}
Kuninori Morimotoe40fadb2019-07-26 13:51:13 +0900328
329int snd_soc_component_is_suspended(struct snd_soc_component *component)
330{
331 return component->suspended;
332}
Kuninori Morimoto08e837d2019-07-26 13:51:17 +0900333
334int snd_soc_component_probe(struct snd_soc_component *component)
335{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900336 int ret = 0;
Kuninori Morimoto08e837d2019-07-26 13:51:17 +0900337
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900338 if (component->driver->probe)
339 ret = component->driver->probe(component);
340
341 return soc_component_ret(component, ret);
Kuninori Morimoto08e837d2019-07-26 13:51:17 +0900342}
Kuninori Morimoto03b34dd2019-07-26 13:51:22 +0900343
344void snd_soc_component_remove(struct snd_soc_component *component)
345{
346 if (component->driver->remove)
347 component->driver->remove(component);
348}
Kuninori Morimoto2c7b1702019-07-26 13:51:26 +0900349
350int snd_soc_component_of_xlate_dai_id(struct snd_soc_component *component,
351 struct device_node *ep)
352{
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900353 int ret = -ENOTSUPP;
Kuninori Morimoto2c7b1702019-07-26 13:51:26 +0900354
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900355 if (component->driver->of_xlate_dai_id)
356 ret = component->driver->of_xlate_dai_id(component, ep);
357
358 return soc_component_ret(component, ret);
Kuninori Morimoto2c7b1702019-07-26 13:51:26 +0900359}
Kuninori Morimotoa2a34172019-07-26 13:51:31 +0900360
361int snd_soc_component_of_xlate_dai_name(struct snd_soc_component *component,
Krzysztof Kozlowski933f98b2021-02-21 16:30:24 +0100362 const struct of_phandle_args *args,
Kuninori Morimotoa2a34172019-07-26 13:51:31 +0900363 const char **dai_name)
364{
365 if (component->driver->of_xlate_dai_name)
Jerome Brunetcc4d8ce2020-07-23 16:20:20 +0200366 return component->driver->of_xlate_dai_name(component,
367 args, dai_name);
368 /*
369 * Don't use soc_component_ret here because we may not want to report
370 * the error just yet. If a device has more than one component, the
371 * first may not match and we don't want spam the log with this.
372 */
373 return -ENOTSUPP;
Kuninori Morimotoa2a34172019-07-26 13:51:31 +0900374}
Kuninori Morimoto0035e252019-07-26 13:51:47 +0900375
Kuninori Morimotoc7d75b52020-06-04 17:06:22 +0900376void snd_soc_component_setup_regmap(struct snd_soc_component *component)
377{
378 int val_bytes = regmap_get_val_bytes(component->regmap);
379
380 /* Errors are legitimate for non-integer byte multiples */
381 if (val_bytes > 0)
382 component->val_bytes = val_bytes;
383}
384
385#ifdef CONFIG_REGMAP
386
387/**
388 * snd_soc_component_init_regmap() - Initialize regmap instance for the
389 * component
390 * @component: The component for which to initialize the regmap instance
391 * @regmap: The regmap instance that should be used by the component
392 *
393 * This function allows deferred assignment of the regmap instance that is
394 * associated with the component. Only use this if the regmap instance is not
395 * yet ready when the component is registered. The function must also be called
396 * before the first IO attempt of the component.
397 */
398void snd_soc_component_init_regmap(struct snd_soc_component *component,
399 struct regmap *regmap)
400{
401 component->regmap = regmap;
402 snd_soc_component_setup_regmap(component);
403}
404EXPORT_SYMBOL_GPL(snd_soc_component_init_regmap);
405
406/**
407 * snd_soc_component_exit_regmap() - De-initialize regmap instance for the
408 * component
409 * @component: The component for which to de-initialize the regmap instance
410 *
411 * Calls regmap_exit() on the regmap instance associated to the component and
412 * removes the regmap instance from the component.
413 *
414 * This function should only be used if snd_soc_component_init_regmap() was used
415 * to initialize the regmap instance.
416 */
417void snd_soc_component_exit_regmap(struct snd_soc_component *component)
418{
419 regmap_exit(component->regmap);
420 component->regmap = NULL;
421}
422EXPORT_SYMBOL_GPL(snd_soc_component_exit_regmap);
423
424#endif
425
Kuninori Morimotof94ba9a2020-11-19 08:50:09 +0900426int snd_soc_component_compr_open(struct snd_compr_stream *cstream)
Kuninori Morimotoa4e427c2020-11-13 13:15:20 +0900427{
428 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
429 struct snd_soc_component *component;
430 int i, ret;
431
432 for_each_rtd_components(rtd, i, component) {
433 if (component->driver->compress_ops &&
434 component->driver->compress_ops->open) {
435 ret = component->driver->compress_ops->open(component, cstream);
Kuninori Morimotof94ba9a2020-11-19 08:50:09 +0900436 if (ret < 0)
Kuninori Morimotoa4e427c2020-11-13 13:15:20 +0900437 return soc_component_ret(component, ret);
Kuninori Morimotoa4e427c2020-11-13 13:15:20 +0900438 }
Kuninori Morimotof94ba9a2020-11-19 08:50:09 +0900439 soc_component_mark_push(component, cstream, compr_open);
Kuninori Morimotoa4e427c2020-11-13 13:15:20 +0900440 }
441
Kuninori Morimotoa4e427c2020-11-13 13:15:20 +0900442 return 0;
443}
444EXPORT_SYMBOL_GPL(snd_soc_component_compr_open);
445
Kuninori Morimotodbde5e212020-11-13 13:15:26 +0900446void snd_soc_component_compr_free(struct snd_compr_stream *cstream,
Kuninori Morimotof94ba9a2020-11-19 08:50:09 +0900447 int rollback)
Kuninori Morimotodbde5e212020-11-13 13:15:26 +0900448{
449 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
450 struct snd_soc_component *component;
451 int i;
452
453 for_each_rtd_components(rtd, i, component) {
Kuninori Morimotof94ba9a2020-11-19 08:50:09 +0900454 if (rollback && !soc_component_mark_match(component, cstream, compr_open))
455 continue;
Kuninori Morimotodbde5e212020-11-13 13:15:26 +0900456
457 if (component->driver->compress_ops &&
458 component->driver->compress_ops->free)
459 component->driver->compress_ops->free(component, cstream);
Kuninori Morimotof94ba9a2020-11-19 08:50:09 +0900460
461 soc_component_mark_pop(component, cstream, compr_open);
Kuninori Morimotodbde5e212020-11-13 13:15:26 +0900462 }
463}
464EXPORT_SYMBOL_GPL(snd_soc_component_compr_free);
465
Kuninori Morimoto08aee252020-11-13 13:15:33 +0900466int snd_soc_component_compr_trigger(struct snd_compr_stream *cstream, int cmd)
467{
468 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
469 struct snd_soc_component *component;
470 int i, ret;
471
472 for_each_rtd_components(rtd, i, component) {
473 if (component->driver->compress_ops &&
474 component->driver->compress_ops->trigger) {
475 ret = component->driver->compress_ops->trigger(
476 component, cstream, cmd);
477 if (ret < 0)
478 return soc_component_ret(component, ret);
479 }
480 }
481
482 return 0;
483}
484EXPORT_SYMBOL_GPL(snd_soc_component_compr_trigger);
485
Kuninori Morimotoff08cf82020-11-13 13:15:49 +0900486int snd_soc_component_compr_set_params(struct snd_compr_stream *cstream,
487 struct snd_compr_params *params)
488{
489 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
490 struct snd_soc_component *component;
491 int i, ret;
492
493 for_each_rtd_components(rtd, i, component) {
494 if (component->driver->compress_ops &&
495 component->driver->compress_ops->set_params) {
496 ret = component->driver->compress_ops->set_params(
497 component, cstream, params);
498 if (ret < 0)
499 return soc_component_ret(component, ret);
500 }
501 }
502
503 return 0;
504}
505EXPORT_SYMBOL_GPL(snd_soc_component_compr_set_params);
506
Kuninori Morimoto77c221e2020-11-13 13:15:56 +0900507int snd_soc_component_compr_get_params(struct snd_compr_stream *cstream,
508 struct snd_codec *params)
509{
510 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
511 struct snd_soc_component *component;
512 int i, ret;
513
514 for_each_rtd_components(rtd, i, component) {
515 if (component->driver->compress_ops &&
516 component->driver->compress_ops->get_params) {
517 ret = component->driver->compress_ops->get_params(
518 component, cstream, params);
519 return soc_component_ret(component, ret);
520 }
521 }
522
523 return 0;
524}
525EXPORT_SYMBOL_GPL(snd_soc_component_compr_get_params);
526
Kuninori Morimotod67fcb22020-11-13 13:16:03 +0900527int snd_soc_component_compr_get_caps(struct snd_compr_stream *cstream,
528 struct snd_compr_caps *caps)
529{
530 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
531 struct snd_soc_component *component;
532 int i, ret = 0;
533
534 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass);
535
536 for_each_rtd_components(rtd, i, component) {
537 if (component->driver->compress_ops &&
538 component->driver->compress_ops->get_caps) {
539 ret = component->driver->compress_ops->get_caps(
540 component, cstream, caps);
541 break;
542 }
543 }
544
545 mutex_unlock(&rtd->card->pcm_mutex);
546
547 return soc_component_ret(component, ret);
548}
549EXPORT_SYMBOL_GPL(snd_soc_component_compr_get_caps);
550
Kuninori Morimoto0f6fe092020-11-13 13:16:11 +0900551int snd_soc_component_compr_get_codec_caps(struct snd_compr_stream *cstream,
552 struct snd_compr_codec_caps *codec)
553{
554 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
555 struct snd_soc_component *component;
556 int i, ret = 0;
557
558 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass);
559
560 for_each_rtd_components(rtd, i, component) {
561 if (component->driver->compress_ops &&
562 component->driver->compress_ops->get_codec_caps) {
563 ret = component->driver->compress_ops->get_codec_caps(
564 component, cstream, codec);
565 break;
566 }
567 }
568
569 mutex_unlock(&rtd->card->pcm_mutex);
570
571 return soc_component_ret(component, ret);
572}
573EXPORT_SYMBOL_GPL(snd_soc_component_compr_get_codec_caps);
574
Kuninori Morimoto0506b882020-11-13 13:16:17 +0900575int snd_soc_component_compr_ack(struct snd_compr_stream *cstream, size_t bytes)
576{
577 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
578 struct snd_soc_component *component;
579 int i, ret;
580
581 for_each_rtd_components(rtd, i, component) {
582 if (component->driver->compress_ops &&
583 component->driver->compress_ops->ack) {
584 ret = component->driver->compress_ops->ack(
585 component, cstream, bytes);
586 if (ret < 0)
587 return soc_component_ret(component, ret);
588 }
589 }
590
591 return 0;
592}
593EXPORT_SYMBOL_GPL(snd_soc_component_compr_ack);
594
Kuninori Morimoto03ecea62020-11-13 13:16:24 +0900595int snd_soc_component_compr_pointer(struct snd_compr_stream *cstream,
596 struct snd_compr_tstamp *tstamp)
597{
598 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
599 struct snd_soc_component *component;
600 int i, ret;
601
602 for_each_rtd_components(rtd, i, component) {
603 if (component->driver->compress_ops &&
604 component->driver->compress_ops->pointer) {
605 ret = component->driver->compress_ops->pointer(
606 component, cstream, tstamp);
607 return soc_component_ret(component, ret);
608 }
609 }
610
611 return 0;
612}
613EXPORT_SYMBOL_GPL(snd_soc_component_compr_pointer);
614
Kuninori Morimotob5852e62020-11-13 13:16:30 +0900615int snd_soc_component_compr_copy(struct snd_compr_stream *cstream,
616 char __user *buf, size_t count)
617{
618 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
619 struct snd_soc_component *component;
620 int i, ret = 0;
621
622 mutex_lock_nested(&rtd->card->pcm_mutex, rtd->card->pcm_subclass);
623
624 for_each_rtd_components(rtd, i, component) {
625 if (component->driver->compress_ops &&
626 component->driver->compress_ops->copy) {
627 ret = component->driver->compress_ops->copy(
628 component, cstream, buf, count);
629 break;
630 }
631 }
632
633 mutex_unlock(&rtd->card->pcm_mutex);
634
635 return soc_component_ret(component, ret);
636}
637EXPORT_SYMBOL_GPL(snd_soc_component_compr_copy);
638
Kuninori Morimoto1b308fb2020-11-13 13:16:36 +0900639int snd_soc_component_compr_set_metadata(struct snd_compr_stream *cstream,
640 struct snd_compr_metadata *metadata)
641{
642 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
643 struct snd_soc_component *component;
644 int i, ret;
645
646 for_each_rtd_components(rtd, i, component) {
647 if (component->driver->compress_ops &&
648 component->driver->compress_ops->set_metadata) {
649 ret = component->driver->compress_ops->set_metadata(
650 component, cstream, metadata);
651 if (ret < 0)
652 return soc_component_ret(component, ret);
653 }
654 }
655
656 return 0;
657}
658EXPORT_SYMBOL_GPL(snd_soc_component_compr_set_metadata);
659
Kuninori Morimotobab78c22020-11-13 13:16:41 +0900660int snd_soc_component_compr_get_metadata(struct snd_compr_stream *cstream,
661 struct snd_compr_metadata *metadata)
662{
663 struct snd_soc_pcm_runtime *rtd = cstream->private_data;
664 struct snd_soc_component *component;
665 int i, ret;
666
667 for_each_rtd_components(rtd, i, component) {
668 if (component->driver->compress_ops &&
669 component->driver->compress_ops->get_metadata) {
670 ret = component->driver->compress_ops->get_metadata(
671 component, cstream, metadata);
672 return soc_component_ret(component, ret);
673 }
674 }
675
676 return 0;
677}
678EXPORT_SYMBOL_GPL(snd_soc_component_compr_get_metadata);
679
Kuninori Morimotoe8712312020-06-16 14:19:52 +0900680static unsigned int soc_component_read_no_lock(
681 struct snd_soc_component *component,
682 unsigned int reg)
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900683{
684 int ret;
Kuninori Morimotocf6e26c2020-06-16 14:19:41 +0900685 unsigned int val = 0;
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900686
687 if (component->regmap)
Kuninori Morimotocf6e26c2020-06-16 14:19:41 +0900688 ret = regmap_read(component->regmap, reg, &val);
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900689 else if (component->driver->read) {
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900690 ret = 0;
Kuninori Morimotocf6e26c2020-06-16 14:19:41 +0900691 val = component->driver->read(component, reg);
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900692 }
693 else
694 ret = -EIO;
695
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900696 if (ret < 0)
Takashi Iwaiefc913c2020-08-10 15:46:31 +0200697 return soc_component_ret(component, ret);
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900698
699 return val;
700}
Kuninori Morimotoe8712312020-06-16 14:19:52 +0900701
702/**
703 * snd_soc_component_read() - Read register value
704 * @component: Component to read from
705 * @reg: Register to read
706 *
707 * Return: read value
708 */
709unsigned int snd_soc_component_read(struct snd_soc_component *component,
710 unsigned int reg)
711{
712 unsigned int val;
713
714 mutex_lock(&component->io_mutex);
715 val = soc_component_read_no_lock(component, reg);
716 mutex_unlock(&component->io_mutex);
717
718 return val;
719}
Kuninori Morimotocf6e26c2020-06-16 14:19:41 +0900720EXPORT_SYMBOL_GPL(snd_soc_component_read);
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900721
Kuninori Morimotoe8712312020-06-16 14:19:52 +0900722static int soc_component_write_no_lock(
723 struct snd_soc_component *component,
724 unsigned int reg, unsigned int val)
725{
726 int ret = -EIO;
727
728 if (component->regmap)
729 ret = regmap_write(component->regmap, reg, val);
730 else if (component->driver->write)
731 ret = component->driver->write(component, reg, val);
732
733 return soc_component_ret(component, ret);
734}
735
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900736/**
737 * snd_soc_component_write() - Write register value
738 * @component: Component to write to
739 * @reg: Register to write
740 * @val: Value to write to the register
741 *
742 * Return: 0 on success, a negative error code otherwise.
743 */
744int snd_soc_component_write(struct snd_soc_component *component,
745 unsigned int reg, unsigned int val)
746{
Kuninori Morimotoe8712312020-06-16 14:19:52 +0900747 int ret;
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900748
Kuninori Morimotoe8712312020-06-16 14:19:52 +0900749 mutex_lock(&component->io_mutex);
750 ret = soc_component_write_no_lock(component, reg, val);
751 mutex_unlock(&component->io_mutex);
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900752
Kuninori Morimotoe8712312020-06-16 14:19:52 +0900753 return ret;
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900754}
755EXPORT_SYMBOL_GPL(snd_soc_component_write);
756
757static int snd_soc_component_update_bits_legacy(
758 struct snd_soc_component *component, unsigned int reg,
759 unsigned int mask, unsigned int val, bool *change)
760{
761 unsigned int old, new;
Kuninori Morimotocf6e26c2020-06-16 14:19:41 +0900762 int ret = 0;
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900763
764 mutex_lock(&component->io_mutex);
765
Kuninori Morimotoe8712312020-06-16 14:19:52 +0900766 old = soc_component_read_no_lock(component, reg);
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900767
768 new = (old & ~mask) | (val & mask);
769 *change = old != new;
770 if (*change)
Kuninori Morimotoe8712312020-06-16 14:19:52 +0900771 ret = soc_component_write_no_lock(component, reg, new);
Kuninori Morimotocf6e26c2020-06-16 14:19:41 +0900772
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900773 mutex_unlock(&component->io_mutex);
774
775 return soc_component_ret(component, ret);
776}
777
778/**
779 * snd_soc_component_update_bits() - Perform read/modify/write cycle
780 * @component: Component to update
781 * @reg: Register to update
782 * @mask: Mask that specifies which bits to update
783 * @val: New value for the bits specified by mask
784 *
785 * Return: 1 if the operation was successful and the value of the register
786 * changed, 0 if the operation was successful, but the value did not change.
787 * Returns a negative error code otherwise.
788 */
789int snd_soc_component_update_bits(struct snd_soc_component *component,
790 unsigned int reg, unsigned int mask, unsigned int val)
791{
792 bool change;
793 int ret;
794
795 if (component->regmap)
796 ret = regmap_update_bits_check(component->regmap, reg, mask,
797 val, &change);
798 else
799 ret = snd_soc_component_update_bits_legacy(component, reg,
800 mask, val, &change);
801
802 if (ret < 0)
803 return soc_component_ret(component, ret);
804 return change;
805}
806EXPORT_SYMBOL_GPL(snd_soc_component_update_bits);
807
808/**
809 * snd_soc_component_update_bits_async() - Perform asynchronous
810 * read/modify/write cycle
811 * @component: Component to update
812 * @reg: Register to update
813 * @mask: Mask that specifies which bits to update
814 * @val: New value for the bits specified by mask
815 *
816 * This function is similar to snd_soc_component_update_bits(), but the update
817 * operation is scheduled asynchronously. This means it may not be completed
818 * when the function returns. To make sure that all scheduled updates have been
819 * completed snd_soc_component_async_complete() must be called.
820 *
821 * Return: 1 if the operation was successful and the value of the register
822 * changed, 0 if the operation was successful, but the value did not change.
823 * Returns a negative error code otherwise.
824 */
825int snd_soc_component_update_bits_async(struct snd_soc_component *component,
826 unsigned int reg, unsigned int mask, unsigned int val)
827{
828 bool change;
829 int ret;
830
831 if (component->regmap)
832 ret = regmap_update_bits_check_async(component->regmap, reg,
833 mask, val, &change);
834 else
835 ret = snd_soc_component_update_bits_legacy(component, reg,
836 mask, val, &change);
837
838 if (ret < 0)
839 return soc_component_ret(component, ret);
840 return change;
841}
842EXPORT_SYMBOL_GPL(snd_soc_component_update_bits_async);
843
844/**
Srinivas Kandagatla1da0b982021-01-26 17:17:48 +0000845 * snd_soc_component_read_field() - Read register field value
846 * @component: Component to read from
847 * @reg: Register to read
848 * @mask: mask of the register field
849 *
850 * Return: read value of register field.
851 */
852unsigned int snd_soc_component_read_field(struct snd_soc_component *component,
853 unsigned int reg, unsigned int mask)
854{
855 unsigned int val;
856
857 val = snd_soc_component_read(component, reg);
858
859 val = (val & mask) >> soc_component_field_shift(component, mask);
860
861 return val;
862}
863EXPORT_SYMBOL_GPL(snd_soc_component_read_field);
864
865/**
866 * snd_soc_component_write_field() - write to register field
867 * @component: Component to write to
868 * @reg: Register to write
869 * @mask: mask of the register field to update
870 * @val: value of the field to write
871 *
872 * Return: 1 for change, otherwise 0.
873 */
874int snd_soc_component_write_field(struct snd_soc_component *component,
875 unsigned int reg, unsigned int mask,
876 unsigned int val)
877{
878
879 val = (val << soc_component_field_shift(component, mask)) & mask;
880
881 return snd_soc_component_update_bits(component, reg, mask, val);
882}
883EXPORT_SYMBOL_GPL(snd_soc_component_write_field);
884
885/**
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900886 * snd_soc_component_async_complete() - Ensure asynchronous I/O has completed
887 * @component: Component for which to wait
888 *
889 * This function blocks until all asynchronous I/O which has previously been
890 * scheduled using snd_soc_component_update_bits_async() has completed.
891 */
892void snd_soc_component_async_complete(struct snd_soc_component *component)
893{
894 if (component->regmap)
895 regmap_async_complete(component->regmap);
896}
897EXPORT_SYMBOL_GPL(snd_soc_component_async_complete);
898
899/**
900 * snd_soc_component_test_bits - Test register for change
901 * @component: component
902 * @reg: Register to test
903 * @mask: Mask that specifies which bits to test
904 * @value: Value to test against
905 *
906 * Tests a register with a new value and checks if the new value is
907 * different from the old value.
908 *
909 * Return: 1 for change, otherwise 0.
910 */
911int snd_soc_component_test_bits(struct snd_soc_component *component,
912 unsigned int reg, unsigned int mask, unsigned int value)
913{
914 unsigned int old, new;
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900915
Kuninori Morimotocf6e26c2020-06-16 14:19:41 +0900916 old = snd_soc_component_read(component, reg);
Kuninori Morimoto460b42d2020-06-04 17:08:03 +0900917 new = (old & ~mask) | value;
918 return old != new;
919}
920EXPORT_SYMBOL_GPL(snd_soc_component_test_bits);
921
Kuninori Morimoto0035e252019-07-26 13:51:47 +0900922int snd_soc_pcm_component_pointer(struct snd_pcm_substream *substream)
923{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +0900924 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimoto0035e252019-07-26 13:51:47 +0900925 struct snd_soc_component *component;
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900926 int i;
Kuninori Morimoto0035e252019-07-26 13:51:47 +0900927
Kuninori Morimoto2b544dd2019-10-15 12:59:31 +0900928 /* FIXME: use 1st pointer */
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900929 for_each_rtd_components(rtd, i, component)
Kuninori Morimotoe2cb4a12019-10-02 14:30:48 +0900930 if (component->driver->pointer)
931 return component->driver->pointer(component, substream);
Kuninori Morimoto0035e252019-07-26 13:51:47 +0900932
933 return 0;
934}
Kuninori Morimoto96a47902019-07-26 13:51:51 +0900935
936int snd_soc_pcm_component_ioctl(struct snd_pcm_substream *substream,
937 unsigned int cmd, void *arg)
938{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +0900939 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimoto96a47902019-07-26 13:51:51 +0900940 struct snd_soc_component *component;
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900941 int i;
Kuninori Morimoto96a47902019-07-26 13:51:51 +0900942
Kuninori Morimoto2b544dd2019-10-15 12:59:31 +0900943 /* FIXME: use 1st ioctl */
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900944 for_each_rtd_components(rtd, i, component)
Kuninori Morimotoe2cb4a12019-10-02 14:30:48 +0900945 if (component->driver->ioctl)
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900946 return soc_component_ret(
947 component,
948 component->driver->ioctl(component,
949 substream, cmd, arg));
Kuninori Morimoto96a47902019-07-26 13:51:51 +0900950
951 return snd_pcm_lib_ioctl(substream, cmd, arg);
952}
Kuninori Morimoto82d81f52019-07-26 13:51:56 +0900953
Takashi Iwai1e5ddb62019-11-21 20:07:09 +0100954int snd_soc_pcm_component_sync_stop(struct snd_pcm_substream *substream)
955{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +0900956 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Takashi Iwai1e5ddb62019-11-21 20:07:09 +0100957 struct snd_soc_component *component;
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900958 int i, ret;
Takashi Iwai1e5ddb62019-11-21 20:07:09 +0100959
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900960 for_each_rtd_components(rtd, i, component) {
Kuninori Morimotof1861a72020-02-28 10:48:35 +0900961 if (component->driver->sync_stop) {
Takashi Iwai1e5ddb62019-11-21 20:07:09 +0100962 ret = component->driver->sync_stop(component,
963 substream);
964 if (ret < 0)
Shengjiu Wangbe75db52020-07-16 13:07:08 +0800965 return soc_component_ret(component, ret);
Takashi Iwai1e5ddb62019-11-21 20:07:09 +0100966 }
967 }
968
969 return 0;
970}
971
Kuninori Morimoto82d81f52019-07-26 13:51:56 +0900972int snd_soc_pcm_component_copy_user(struct snd_pcm_substream *substream,
973 int channel, unsigned long pos,
974 void __user *buf, unsigned long bytes)
975{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +0900976 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimoto82d81f52019-07-26 13:51:56 +0900977 struct snd_soc_component *component;
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900978 int i;
Kuninori Morimoto82d81f52019-07-26 13:51:56 +0900979
Kuninori Morimoto2b544dd2019-10-15 12:59:31 +0900980 /* FIXME. it returns 1st copy now */
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900981 for_each_rtd_components(rtd, i, component)
Kuninori Morimotoe2cb4a12019-10-02 14:30:48 +0900982 if (component->driver->copy_user)
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +0900983 return soc_component_ret(
984 component,
985 component->driver->copy_user(
986 component, substream, channel,
987 pos, buf, bytes));
Kuninori Morimoto82d81f52019-07-26 13:51:56 +0900988
989 return -EINVAL;
990}
Kuninori Morimoto9c712e42019-07-26 13:52:00 +0900991
992struct page *snd_soc_pcm_component_page(struct snd_pcm_substream *substream,
993 unsigned long offset)
994{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +0900995 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimoto9c712e42019-07-26 13:52:00 +0900996 struct snd_soc_component *component;
997 struct page *page;
Kuninori Morimoto613fb502020-01-10 11:35:21 +0900998 int i;
Kuninori Morimoto9c712e42019-07-26 13:52:00 +0900999
Kuninori Morimoto2b544dd2019-10-15 12:59:31 +09001000 /* FIXME. it returns 1st page now */
Kuninori Morimoto613fb502020-01-10 11:35:21 +09001001 for_each_rtd_components(rtd, i, component) {
Kuninori Morimotoe2cb4a12019-10-02 14:30:48 +09001002 if (component->driver->page) {
1003 page = component->driver->page(component,
1004 substream, offset);
1005 if (page)
1006 return page;
1007 }
Kuninori Morimoto9c712e42019-07-26 13:52:00 +09001008 }
1009
1010 return NULL;
1011}
Kuninori Morimoto205875e2019-07-26 13:52:04 +09001012
1013int snd_soc_pcm_component_mmap(struct snd_pcm_substream *substream,
1014 struct vm_area_struct *vma)
1015{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +09001016 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimoto205875e2019-07-26 13:52:04 +09001017 struct snd_soc_component *component;
Kuninori Morimoto613fb502020-01-10 11:35:21 +09001018 int i;
Kuninori Morimoto205875e2019-07-26 13:52:04 +09001019
Kuninori Morimoto2b544dd2019-10-15 12:59:31 +09001020 /* FIXME. it returns 1st mmap now */
Kuninori Morimoto613fb502020-01-10 11:35:21 +09001021 for_each_rtd_components(rtd, i, component)
Kuninori Morimotoe2cb4a12019-10-02 14:30:48 +09001022 if (component->driver->mmap)
Shengjiu Wangbe75db52020-07-16 13:07:08 +08001023 return soc_component_ret(
Kuninori Morimotoe2329ee2020-06-04 17:06:41 +09001024 component,
1025 component->driver->mmap(component,
1026 substream, vma));
Kuninori Morimoto205875e2019-07-26 13:52:04 +09001027
1028 return -EINVAL;
1029}
Kuninori Morimoto74842912019-07-26 13:52:08 +09001030
Kuninori Morimotob2b2afb2019-11-18 10:50:32 +09001031int snd_soc_pcm_component_new(struct snd_soc_pcm_runtime *rtd)
Kuninori Morimoto74842912019-07-26 13:52:08 +09001032{
Kuninori Morimoto74842912019-07-26 13:52:08 +09001033 struct snd_soc_component *component;
1034 int ret;
Kuninori Morimoto613fb502020-01-10 11:35:21 +09001035 int i;
Kuninori Morimoto74842912019-07-26 13:52:08 +09001036
Kuninori Morimoto613fb502020-01-10 11:35:21 +09001037 for_each_rtd_components(rtd, i, component) {
Kuninori Morimotoc64bfc92019-10-02 14:30:59 +09001038 if (component->driver->pcm_construct) {
1039 ret = component->driver->pcm_construct(component, rtd);
1040 if (ret < 0)
Shengjiu Wangbe75db52020-07-16 13:07:08 +08001041 return soc_component_ret(component, ret);
Kuninori Morimotoc64bfc92019-10-02 14:30:59 +09001042 }
Kuninori Morimoto74842912019-07-26 13:52:08 +09001043 }
1044
1045 return 0;
1046}
Kuninori Morimoto79776da2019-07-26 13:52:12 +09001047
Kuninori Morimotob2b2afb2019-11-18 10:50:32 +09001048void snd_soc_pcm_component_free(struct snd_soc_pcm_runtime *rtd)
Kuninori Morimoto79776da2019-07-26 13:52:12 +09001049{
Kuninori Morimoto79776da2019-07-26 13:52:12 +09001050 struct snd_soc_component *component;
Kuninori Morimoto613fb502020-01-10 11:35:21 +09001051 int i;
Kuninori Morimoto79776da2019-07-26 13:52:12 +09001052
Takashi Iwai8e3366c2020-01-07 08:09:56 +01001053 if (!rtd->pcm)
1054 return;
1055
Kuninori Morimoto613fb502020-01-10 11:35:21 +09001056 for_each_rtd_components(rtd, i, component)
Kuninori Morimotoc64bfc92019-10-02 14:30:59 +09001057 if (component->driver->pcm_destruct)
Kuninori Morimotob2b2afb2019-11-18 10:50:32 +09001058 component->driver->pcm_destruct(component, rtd->pcm);
Kuninori Morimoto79776da2019-07-26 13:52:12 +09001059}
Kuninori Morimoto4f395142020-06-04 17:06:58 +09001060
1061int snd_soc_pcm_component_prepare(struct snd_pcm_substream *substream)
1062{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +09001063 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimoto4f395142020-06-04 17:06:58 +09001064 struct snd_soc_component *component;
1065 int i, ret;
1066
1067 for_each_rtd_components(rtd, i, component) {
1068 if (component->driver->prepare) {
1069 ret = component->driver->prepare(component, substream);
1070 if (ret < 0)
1071 return soc_component_ret(component, ret);
1072 }
1073 }
1074
1075 return 0;
1076}
Kuninori Morimotoe1bafa82020-06-04 17:07:11 +09001077
1078int snd_soc_pcm_component_hw_params(struct snd_pcm_substream *substream,
Kuninori Morimoto3a36a642020-09-29 13:31:41 +09001079 struct snd_pcm_hw_params *params)
Kuninori Morimotoe1bafa82020-06-04 17:07:11 +09001080{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +09001081 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimotoe1bafa82020-06-04 17:07:11 +09001082 struct snd_soc_component *component;
1083 int i, ret;
1084
1085 for_each_rtd_components(rtd, i, component) {
1086 if (component->driver->hw_params) {
1087 ret = component->driver->hw_params(component,
1088 substream, params);
Kuninori Morimoto3a36a642020-09-29 13:31:41 +09001089 if (ret < 0)
Kuninori Morimotoe1bafa82020-06-04 17:07:11 +09001090 return soc_component_ret(component, ret);
Kuninori Morimotoe1bafa82020-06-04 17:07:11 +09001091 }
Kuninori Morimoto3a36a642020-09-29 13:31:41 +09001092 /* mark substream if succeeded */
1093 soc_component_mark_push(component, substream, hw_params);
Kuninori Morimotoe1bafa82020-06-04 17:07:11 +09001094 }
1095
Kuninori Morimotoe1bafa82020-06-04 17:07:11 +09001096 return 0;
1097}
Kuninori Morimoto04751112020-06-04 17:07:24 +09001098
1099void snd_soc_pcm_component_hw_free(struct snd_pcm_substream *substream,
Kuninori Morimoto3a36a642020-09-29 13:31:41 +09001100 int rollback)
Kuninori Morimoto04751112020-06-04 17:07:24 +09001101{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +09001102 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimoto04751112020-06-04 17:07:24 +09001103 struct snd_soc_component *component;
1104 int i, ret;
1105
1106 for_each_rtd_components(rtd, i, component) {
Kuninori Morimoto3a36a642020-09-29 13:31:41 +09001107 if (rollback && !soc_component_mark_match(component, substream, hw_params))
1108 continue;
Kuninori Morimoto04751112020-06-04 17:07:24 +09001109
1110 if (component->driver->hw_free) {
1111 ret = component->driver->hw_free(component, substream);
1112 if (ret < 0)
1113 soc_component_ret(component, ret);
1114 }
Kuninori Morimoto3a36a642020-09-29 13:31:41 +09001115
1116 /* remove marked substream */
1117 soc_component_mark_pop(component, substream, hw_params);
Kuninori Morimoto04751112020-06-04 17:07:24 +09001118 }
1119}
Kuninori Morimoto32fd1202020-06-04 17:07:40 +09001120
Kuninori Morimoto6374f492020-12-01 08:51:33 +09001121static int soc_component_trigger(struct snd_soc_component *component,
1122 struct snd_pcm_substream *substream,
1123 int cmd)
1124{
1125 int ret = 0;
1126
1127 if (component->driver->trigger)
1128 ret = component->driver->trigger(component, substream, cmd);
1129
1130 return soc_component_ret(component, ret);
1131}
1132
Kuninori Morimoto32fd1202020-06-04 17:07:40 +09001133int snd_soc_pcm_component_trigger(struct snd_pcm_substream *substream,
Kuninori Morimoto6374f492020-12-01 08:51:33 +09001134 int cmd, int rollback)
Kuninori Morimoto32fd1202020-06-04 17:07:40 +09001135{
Kuninori Morimoto0ceef682020-07-20 10:17:39 +09001136 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
Kuninori Morimoto32fd1202020-06-04 17:07:40 +09001137 struct snd_soc_component *component;
Kuninori Morimoto6374f492020-12-01 08:51:33 +09001138 int i, r, ret = 0;
Kuninori Morimoto32fd1202020-06-04 17:07:40 +09001139
Kuninori Morimoto6374f492020-12-01 08:51:33 +09001140 switch (cmd) {
1141 case SNDRV_PCM_TRIGGER_START:
1142 case SNDRV_PCM_TRIGGER_RESUME:
1143 case SNDRV_PCM_TRIGGER_PAUSE_RELEASE:
1144 for_each_rtd_components(rtd, i, component) {
1145 ret = soc_component_trigger(component, substream, cmd);
Kuninori Morimoto32fd1202020-06-04 17:07:40 +09001146 if (ret < 0)
Kuninori Morimoto6374f492020-12-01 08:51:33 +09001147 break;
1148 soc_component_mark_push(component, substream, trigger);
1149 }
1150 break;
1151 case SNDRV_PCM_TRIGGER_STOP:
1152 case SNDRV_PCM_TRIGGER_SUSPEND:
1153 case SNDRV_PCM_TRIGGER_PAUSE_PUSH:
1154 for_each_rtd_components(rtd, i, component) {
1155 if (rollback && !soc_component_mark_match(component, substream, trigger))
1156 continue;
1157
1158 r = soc_component_trigger(component, substream, cmd);
1159 if (r < 0)
1160 ret = r; /* use last ret */
1161 soc_component_mark_pop(component, substream, trigger);
Kuninori Morimoto32fd1202020-06-04 17:07:40 +09001162 }
1163 }
1164
Kuninori Morimoto6374f492020-12-01 08:51:33 +09001165 return ret;
Kuninori Morimoto32fd1202020-06-04 17:07:40 +09001166}
Kuninori Morimoto939a5cf2020-09-28 09:01:17 +09001167
1168int snd_soc_pcm_component_pm_runtime_get(struct snd_soc_pcm_runtime *rtd,
1169 void *stream)
1170{
1171 struct snd_soc_component *component;
Kuninori Morimoto500b39d2021-08-16 13:56:19 +09001172 int i;
Kuninori Morimoto939a5cf2020-09-28 09:01:17 +09001173
1174 for_each_rtd_components(rtd, i, component) {
Kuninori Morimoto500b39d2021-08-16 13:56:19 +09001175 int ret = pm_runtime_get_sync(component->dev);
Kuninori Morimoto939a5cf2020-09-28 09:01:17 +09001176 if (ret < 0 && ret != -EACCES) {
1177 pm_runtime_put_noidle(component->dev);
1178 return soc_component_ret(component, ret);
1179 }
1180 /* mark stream if succeeded */
1181 soc_component_mark_push(component, stream, pm);
1182 }
1183
1184 return 0;
1185}
1186
1187void snd_soc_pcm_component_pm_runtime_put(struct snd_soc_pcm_runtime *rtd,
1188 void *stream, int rollback)
1189{
1190 struct snd_soc_component *component;
1191 int i;
1192
1193 for_each_rtd_components(rtd, i, component) {
1194 if (rollback && !soc_component_mark_match(component, stream, pm))
1195 continue;
1196
1197 pm_runtime_mark_last_busy(component->dev);
1198 pm_runtime_put_autosuspend(component->dev);
1199
1200 /* remove marked stream */
1201 soc_component_mark_pop(component, stream, pm);
1202 }
1203}
Shengjiu Wang8bdfc042021-03-12 10:38:40 +08001204
1205int snd_soc_pcm_component_ack(struct snd_pcm_substream *substream)
1206{
1207 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream);
1208 struct snd_soc_component *component;
1209 int i;
1210
1211 /* FIXME: use 1st pointer */
1212 for_each_rtd_components(rtd, i, component)
1213 if (component->driver->ack)
1214 return component->driver->ack(component, substream);
1215
1216 return 0;
1217}