Lines Matching +full:data +full:- +full:size

1 // SPDX-License-Identifier: (GPL-2.0-only OR BSD-3-Clause)
15 #include "sof-priv.h"
16 #include "sof-audio.h"
26 mask = 1U << snd_ctl_get_ioffidx(kcontrol, &ucontrol->id); in update_mute_led()
28 for (i = 0; i < scontrol->num_channels; i++) { in update_mute_led()
29 if (ucontrol->value.integer.value[i]) { in update_mute_led()
35 if (temp == scontrol->led_ctl.led_value) in update_mute_led()
38 scontrol->led_ctl.led_value = temp; in update_mute_led()
41 if (!scontrol->led_ctl.direction) in update_mute_led()
48 static inline u32 mixer_to_ipc(unsigned int value, u32 *volume_map, int size) in mixer_to_ipc() argument
50 if (value >= size) in mixer_to_ipc()
51 return volume_map[size - 1]; in mixer_to_ipc()
56 static inline u32 ipc_to_mixer(u32 value, u32 *volume_map, int size) in ipc_to_mixer() argument
60 for (i = 0; i < size; i++) { in ipc_to_mixer()
65 return i - 1; in ipc_to_mixer()
72 (struct soc_mixer_control *)kcontrol->private_value; in snd_sof_volume_get()
73 struct snd_sof_control *scontrol = sm->dobj.private; in snd_sof_volume_get()
74 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_volume_get()
75 unsigned int i, channels = scontrol->num_channels; in snd_sof_volume_get()
79 ucontrol->value.integer.value[i] = in snd_sof_volume_get()
80 ipc_to_mixer(cdata->chanv[i].value, in snd_sof_volume_get()
81 scontrol->volume_table, sm->max + 1); in snd_sof_volume_get()
90 (struct soc_mixer_control *)kcontrol->private_value; in snd_sof_volume_put()
91 struct snd_sof_control *scontrol = sm->dobj.private; in snd_sof_volume_put()
92 struct snd_soc_component *scomp = scontrol->scomp; in snd_sof_volume_put()
93 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_volume_put()
94 unsigned int i, channels = scontrol->num_channels; in snd_sof_volume_put()
100 value = mixer_to_ipc(ucontrol->value.integer.value[i], in snd_sof_volume_put()
101 scontrol->volume_table, sm->max + 1); in snd_sof_volume_put()
102 change = change || (value != cdata->chanv[i].value); in snd_sof_volume_put()
103 cdata->chanv[i].channel = i; in snd_sof_volume_put()
104 cdata->chanv[i].value = value; in snd_sof_volume_put()
108 if (pm_runtime_active(scomp->dev)) in snd_sof_volume_put()
119 struct soc_mixer_control *sm = (struct soc_mixer_control *)kcontrol->private_value; in snd_sof_volume_info()
120 struct snd_sof_control *scontrol = sm->dobj.private; in snd_sof_volume_info()
121 unsigned int channels = scontrol->num_channels; in snd_sof_volume_info()
124 if (!sm->platform_max) in snd_sof_volume_info()
125 sm->platform_max = sm->max; in snd_sof_volume_info()
126 platform_max = sm->platform_max; in snd_sof_volume_info()
128 if (platform_max == 1 && !strstr(kcontrol->id.name, " Volume")) in snd_sof_volume_info()
129 uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; in snd_sof_volume_info()
131 uinfo->type = SNDRV_CTL_ELEM_TYPE_INTEGER; in snd_sof_volume_info()
133 uinfo->count = channels; in snd_sof_volume_info()
134 uinfo->value.integer.min = 0; in snd_sof_volume_info()
135 uinfo->value.integer.max = platform_max - sm->min; in snd_sof_volume_info()
143 (struct soc_mixer_control *)kcontrol->private_value; in snd_sof_switch_get()
144 struct snd_sof_control *scontrol = sm->dobj.private; in snd_sof_switch_get()
145 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_switch_get()
146 unsigned int i, channels = scontrol->num_channels; in snd_sof_switch_get()
150 ucontrol->value.integer.value[i] = cdata->chanv[i].value; in snd_sof_switch_get()
159 (struct soc_mixer_control *)kcontrol->private_value; in snd_sof_switch_put()
160 struct snd_sof_control *scontrol = sm->dobj.private; in snd_sof_switch_put()
161 struct snd_soc_component *scomp = scontrol->scomp; in snd_sof_switch_put()
162 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_switch_put()
163 unsigned int i, channels = scontrol->num_channels; in snd_sof_switch_put()
169 value = ucontrol->value.integer.value[i]; in snd_sof_switch_put()
170 change = change || (value != cdata->chanv[i].value); in snd_sof_switch_put()
171 cdata->chanv[i].channel = i; in snd_sof_switch_put()
172 cdata->chanv[i].value = value; in snd_sof_switch_put()
175 if (scontrol->led_ctl.use_led) in snd_sof_switch_put()
179 if (pm_runtime_active(scomp->dev)) in snd_sof_switch_put()
193 (struct soc_enum *)kcontrol->private_value; in snd_sof_enum_get()
194 struct snd_sof_control *scontrol = se->dobj.private; in snd_sof_enum_get()
195 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_enum_get()
196 unsigned int i, channels = scontrol->num_channels; in snd_sof_enum_get()
200 ucontrol->value.enumerated.item[i] = cdata->chanv[i].value; in snd_sof_enum_get()
209 (struct soc_enum *)kcontrol->private_value; in snd_sof_enum_put()
210 struct snd_sof_control *scontrol = se->dobj.private; in snd_sof_enum_put()
211 struct snd_soc_component *scomp = scontrol->scomp; in snd_sof_enum_put()
212 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_enum_put()
213 unsigned int i, channels = scontrol->num_channels; in snd_sof_enum_put()
219 value = ucontrol->value.enumerated.item[i]; in snd_sof_enum_put()
220 change = change || (value != cdata->chanv[i].value); in snd_sof_enum_put()
221 cdata->chanv[i].channel = i; in snd_sof_enum_put()
222 cdata->chanv[i].value = value; in snd_sof_enum_put()
226 if (pm_runtime_active(scomp->dev)) in snd_sof_enum_put()
240 (struct soc_bytes_ext *)kcontrol->private_value; in snd_sof_bytes_get()
241 struct snd_sof_control *scontrol = be->dobj.private; in snd_sof_bytes_get()
242 struct snd_soc_component *scomp = scontrol->scomp; in snd_sof_bytes_get()
243 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_bytes_get()
244 struct sof_abi_hdr *data = cdata->data; in snd_sof_bytes_get() local
245 size_t size; in snd_sof_bytes_get() local
247 if (be->max > sizeof(ucontrol->value.bytes.data)) { in snd_sof_bytes_get()
248 dev_err_ratelimited(scomp->dev, in snd_sof_bytes_get()
249 "error: data max %d exceeds ucontrol data array size\n", in snd_sof_bytes_get()
250 be->max); in snd_sof_bytes_get()
251 return -EINVAL; in snd_sof_bytes_get()
254 /* be->max has been verified to be >= sizeof(struct sof_abi_hdr) */ in snd_sof_bytes_get()
255 if (data->size > be->max - sizeof(*data)) { in snd_sof_bytes_get()
256 dev_err_ratelimited(scomp->dev, in snd_sof_bytes_get()
257 "error: %u bytes of control data is invalid, max is %zu\n", in snd_sof_bytes_get()
258 data->size, be->max - sizeof(*data)); in snd_sof_bytes_get()
259 return -EINVAL; in snd_sof_bytes_get()
262 size = data->size + sizeof(*data); in snd_sof_bytes_get()
265 memcpy(ucontrol->value.bytes.data, data, size); in snd_sof_bytes_get()
274 (struct soc_bytes_ext *)kcontrol->private_value; in snd_sof_bytes_put()
275 struct snd_sof_control *scontrol = be->dobj.private; in snd_sof_bytes_put()
276 struct snd_soc_component *scomp = scontrol->scomp; in snd_sof_bytes_put()
277 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_bytes_put()
278 struct sof_abi_hdr *data = cdata->data; in snd_sof_bytes_put() local
279 size_t size; in snd_sof_bytes_put() local
281 if (be->max > sizeof(ucontrol->value.bytes.data)) { in snd_sof_bytes_put()
282 dev_err_ratelimited(scomp->dev, in snd_sof_bytes_put()
283 "error: data max %d exceeds ucontrol data array size\n", in snd_sof_bytes_put()
284 be->max); in snd_sof_bytes_put()
285 return -EINVAL; in snd_sof_bytes_put()
288 /* be->max has been verified to be >= sizeof(struct sof_abi_hdr) */ in snd_sof_bytes_put()
289 if (data->size > be->max - sizeof(*data)) { in snd_sof_bytes_put()
290 dev_err_ratelimited(scomp->dev, in snd_sof_bytes_put()
291 "error: data size too big %u bytes max is %zu\n", in snd_sof_bytes_put()
292 data->size, be->max - sizeof(*data)); in snd_sof_bytes_put()
293 return -EINVAL; in snd_sof_bytes_put()
296 size = data->size + sizeof(*data); in snd_sof_bytes_put()
299 memcpy(data, ucontrol->value.bytes.data, size); in snd_sof_bytes_put()
302 if (pm_runtime_active(scomp->dev)) in snd_sof_bytes_put()
306 scontrol->cmd, in snd_sof_bytes_put()
314 unsigned int size) in snd_sof_bytes_ext_put() argument
317 (struct soc_bytes_ext *)kcontrol->private_value; in snd_sof_bytes_ext_put()
318 struct snd_sof_control *scontrol = be->dobj.private; in snd_sof_bytes_ext_put()
319 struct snd_soc_component *scomp = scontrol->scomp; in snd_sof_bytes_ext_put()
320 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_bytes_ext_put()
326 if (size < sizeof(struct snd_ctl_tlv)) in snd_sof_bytes_ext_put()
327 return -EINVAL; in snd_sof_bytes_ext_put()
330 * The beginning of bytes data contains a header from where in snd_sof_bytes_ext_put()
332 * length of data from tlvd->tlv. in snd_sof_bytes_ext_put()
335 return -EFAULT; in snd_sof_bytes_ext_put()
338 if (header.length + sizeof(struct snd_ctl_tlv) > size) { in snd_sof_bytes_ext_put()
339 dev_err_ratelimited(scomp->dev, "error: inconsistent TLV, data %d + header %zu > %d\n", in snd_sof_bytes_ext_put()
340 header.length, sizeof(struct snd_ctl_tlv), size); in snd_sof_bytes_ext_put()
341 return -EINVAL; in snd_sof_bytes_ext_put()
344 /* be->max is coming from topology */ in snd_sof_bytes_ext_put()
345 if (header.length > be->max) { in snd_sof_bytes_ext_put()
346 dev_err_ratelimited(scomp->dev, "error: Bytes data size %d exceeds max %d.\n", in snd_sof_bytes_ext_put()
347 header.length, be->max); in snd_sof_bytes_ext_put()
348 return -EINVAL; in snd_sof_bytes_ext_put()
352 if (header.numid != scontrol->cmd) { in snd_sof_bytes_ext_put()
353 dev_err_ratelimited(scomp->dev, in snd_sof_bytes_ext_put()
356 return -EINVAL; in snd_sof_bytes_ext_put()
359 if (copy_from_user(cdata->data, tlvd->tlv, header.length)) in snd_sof_bytes_ext_put()
360 return -EFAULT; in snd_sof_bytes_ext_put()
362 if (cdata->data->magic != SOF_ABI_MAGIC) { in snd_sof_bytes_ext_put()
363 dev_err_ratelimited(scomp->dev, in snd_sof_bytes_ext_put()
365 cdata->data->magic); in snd_sof_bytes_ext_put()
366 return -EINVAL; in snd_sof_bytes_ext_put()
369 if (SOF_ABI_VERSION_INCOMPATIBLE(SOF_ABI_VERSION, cdata->data->abi)) { in snd_sof_bytes_ext_put()
370 dev_err_ratelimited(scomp->dev, "error: Incompatible ABI version 0x%08x.\n", in snd_sof_bytes_ext_put()
371 cdata->data->abi); in snd_sof_bytes_ext_put()
372 return -EINVAL; in snd_sof_bytes_ext_put()
375 /* be->max has been verified to be >= sizeof(struct sof_abi_hdr) */ in snd_sof_bytes_ext_put()
376 if (cdata->data->size > be->max - sizeof(struct sof_abi_hdr)) { in snd_sof_bytes_ext_put()
377 dev_err_ratelimited(scomp->dev, "error: Mismatch in ABI data size (truncated?).\n"); in snd_sof_bytes_ext_put()
378 return -EINVAL; in snd_sof_bytes_ext_put()
382 if (pm_runtime_active(scomp->dev)) in snd_sof_bytes_ext_put()
386 scontrol->cmd, in snd_sof_bytes_ext_put()
393 unsigned int size) in snd_sof_bytes_ext_volatile_get() argument
395 struct soc_bytes_ext *be = (struct soc_bytes_ext *)kcontrol->private_value; in snd_sof_bytes_ext_volatile_get()
396 struct snd_sof_control *scontrol = be->dobj.private; in snd_sof_bytes_ext_volatile_get()
397 struct snd_soc_component *scomp = scontrol->scomp; in snd_sof_bytes_ext_volatile_get()
398 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_bytes_ext_volatile_get()
406 * Decrement the limit by ext bytes header size to in snd_sof_bytes_ext_volatile_get()
409 if (size < sizeof(struct snd_ctl_tlv)) in snd_sof_bytes_ext_volatile_get()
410 return -ENOSPC; in snd_sof_bytes_ext_volatile_get()
411 size -= sizeof(struct snd_ctl_tlv); in snd_sof_bytes_ext_volatile_get()
413 ret = pm_runtime_get_sync(scomp->dev); in snd_sof_bytes_ext_volatile_get()
414 if (ret < 0 && ret != -EACCES) { in snd_sof_bytes_ext_volatile_get()
415 dev_err_ratelimited(scomp->dev, "error: bytes_ext get failed to resume %d\n", ret); in snd_sof_bytes_ext_volatile_get()
416 pm_runtime_put_noidle(scomp->dev); in snd_sof_bytes_ext_volatile_get()
421 cdata->data->magic = SOF_ABI_MAGIC; in snd_sof_bytes_ext_volatile_get()
422 cdata->data->abi = SOF_ABI_VERSION; in snd_sof_bytes_ext_volatile_get()
423 /* get all the component data from DSP */ in snd_sof_bytes_ext_volatile_get()
425 scontrol->cmd, false); in snd_sof_bytes_ext_volatile_get()
429 /* check data size doesn't exceed max coming from topology */ in snd_sof_bytes_ext_volatile_get()
430 if (cdata->data->size > be->max - sizeof(struct sof_abi_hdr)) { in snd_sof_bytes_ext_volatile_get()
431 dev_err_ratelimited(scomp->dev, "error: user data size %d exceeds max size %zu.\n", in snd_sof_bytes_ext_volatile_get()
432 cdata->data->size, in snd_sof_bytes_ext_volatile_get()
433 be->max - sizeof(struct sof_abi_hdr)); in snd_sof_bytes_ext_volatile_get()
434 ret = -EINVAL; in snd_sof_bytes_ext_volatile_get()
438 data_size = cdata->data->size + sizeof(struct sof_abi_hdr); in snd_sof_bytes_ext_volatile_get()
440 /* make sure we don't exceed size provided by user space for data */ in snd_sof_bytes_ext_volatile_get()
441 if (data_size > size) { in snd_sof_bytes_ext_volatile_get()
442 ret = -ENOSPC; in snd_sof_bytes_ext_volatile_get()
446 header.numid = scontrol->cmd; in snd_sof_bytes_ext_volatile_get()
449 ret = -EFAULT; in snd_sof_bytes_ext_volatile_get()
453 if (copy_to_user(tlvd->tlv, cdata->data, data_size)) in snd_sof_bytes_ext_volatile_get()
454 ret = -EFAULT; in snd_sof_bytes_ext_volatile_get()
456 pm_runtime_mark_last_busy(scomp->dev); in snd_sof_bytes_ext_volatile_get()
457 err = pm_runtime_put_autosuspend(scomp->dev); in snd_sof_bytes_ext_volatile_get()
459 dev_err_ratelimited(scomp->dev, "error: bytes_ext get failed to idle %d\n", err); in snd_sof_bytes_ext_volatile_get()
466 unsigned int size) in snd_sof_bytes_ext_get() argument
469 (struct soc_bytes_ext *)kcontrol->private_value; in snd_sof_bytes_ext_get()
470 struct snd_sof_control *scontrol = be->dobj.private; in snd_sof_bytes_ext_get()
471 struct snd_soc_component *scomp = scontrol->scomp; in snd_sof_bytes_ext_get()
472 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; in snd_sof_bytes_ext_get()
479 * Decrement the limit by ext bytes header size to in snd_sof_bytes_ext_get()
482 if (size < sizeof(struct snd_ctl_tlv)) in snd_sof_bytes_ext_get()
483 return -ENOSPC; in snd_sof_bytes_ext_get()
484 size -= sizeof(struct snd_ctl_tlv); in snd_sof_bytes_ext_get()
487 cdata->data->magic = SOF_ABI_MAGIC; in snd_sof_bytes_ext_get()
488 cdata->data->abi = SOF_ABI_VERSION; in snd_sof_bytes_ext_get()
490 /* check data size doesn't exceed max coming from topology */ in snd_sof_bytes_ext_get()
491 if (cdata->data->size > be->max - sizeof(struct sof_abi_hdr)) { in snd_sof_bytes_ext_get()
492 dev_err_ratelimited(scomp->dev, "error: user data size %d exceeds max size %zu.\n", in snd_sof_bytes_ext_get()
493 cdata->data->size, in snd_sof_bytes_ext_get()
494 be->max - sizeof(struct sof_abi_hdr)); in snd_sof_bytes_ext_get()
495 return -EINVAL; in snd_sof_bytes_ext_get()
498 data_size = cdata->data->size + sizeof(struct sof_abi_hdr); in snd_sof_bytes_ext_get()
500 /* make sure we don't exceed size provided by user space for data */ in snd_sof_bytes_ext_get()
501 if (data_size > size) in snd_sof_bytes_ext_get()
502 return -ENOSPC; in snd_sof_bytes_ext_get()
504 header.numid = scontrol->cmd; in snd_sof_bytes_ext_get()
507 return -EFAULT; in snd_sof_bytes_ext_get()
509 if (copy_to_user(tlvd->tlv, cdata->data, data_size)) in snd_sof_bytes_ext_get()
510 return -EFAULT; in snd_sof_bytes_ext_get()