1 // SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause) 2 // 3 // This file is provided under a dual BSD/GPLv2 license. When using or 4 // redistributing this file, you may do so under either license. 5 // 6 // Copyright(c) 2018 Intel Corporation. All rights reserved. 7 // 8 // Author: Liam Girdwood <liam.r.girdwood@linux.intel.com> 9 // 10 11 /* Mixer Controls */ 12 13 #include <linux/pm_runtime.h> 14 #include "sof-priv.h" 15 16 static inline u32 mixer_to_ipc(unsigned int value, u32 *volume_map, int size) 17 { 18 if (value >= size) 19 return volume_map[size - 1]; 20 21 return volume_map[value]; 22 } 23 24 static inline u32 ipc_to_mixer(u32 value, u32 *volume_map, int size) 25 { 26 int i; 27 28 for (i = 0; i < size; i++) { 29 if (volume_map[i] >= value) 30 return i; 31 } 32 33 return i - 1; 34 } 35 36 int snd_sof_volume_get(struct snd_kcontrol *kcontrol, 37 struct snd_ctl_elem_value *ucontrol) 38 { 39 struct soc_mixer_control *sm = 40 (struct soc_mixer_control *)kcontrol->private_value; 41 struct snd_sof_control *scontrol = sm->dobj.private; 42 struct snd_sof_dev *sdev = scontrol->sdev; 43 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 44 unsigned int i, channels = scontrol->num_channels; 45 int err, ret; 46 47 ret = pm_runtime_get_sync(sdev->dev); 48 if (ret < 0) { 49 dev_err_ratelimited(sdev->dev, 50 "error: volume get failed to resume %d\n", 51 ret); 52 pm_runtime_put_noidle(sdev->dev); 53 return ret; 54 } 55 56 /* get all the mixer data from DSP */ 57 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 58 SOF_IPC_COMP_GET_VALUE, 59 SOF_CTRL_TYPE_VALUE_CHAN_GET, 60 SOF_CTRL_CMD_VOLUME, 61 false); 62 63 /* read back each channel */ 64 for (i = 0; i < channels; i++) 65 ucontrol->value.integer.value[i] = 66 ipc_to_mixer(cdata->chanv[i].value, 67 scontrol->volume_table, sm->max + 1); 68 69 pm_runtime_mark_last_busy(sdev->dev); 70 err = pm_runtime_put_autosuspend(sdev->dev); 71 if (err < 0) 72 dev_err_ratelimited(sdev->dev, 73 "error: volume get failed to idle %d\n", 74 err); 75 return 0; 76 } 77 78 int snd_sof_volume_put(struct snd_kcontrol *kcontrol, 79 struct snd_ctl_elem_value *ucontrol) 80 { 81 struct soc_mixer_control *sm = 82 (struct soc_mixer_control *)kcontrol->private_value; 83 struct snd_sof_control *scontrol = sm->dobj.private; 84 struct snd_sof_dev *sdev = scontrol->sdev; 85 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 86 unsigned int i, channels = scontrol->num_channels; 87 int ret, err; 88 89 ret = pm_runtime_get_sync(sdev->dev); 90 if (ret < 0) { 91 dev_err_ratelimited(sdev->dev, 92 "error: volume put failed to resume %d\n", 93 ret); 94 pm_runtime_put_noidle(sdev->dev); 95 return ret; 96 } 97 98 /* update each channel */ 99 for (i = 0; i < channels; i++) { 100 cdata->chanv[i].value = 101 mixer_to_ipc(ucontrol->value.integer.value[i], 102 scontrol->volume_table, sm->max + 1); 103 cdata->chanv[i].channel = i; 104 } 105 106 /* notify DSP of mixer updates */ 107 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 108 SOF_IPC_COMP_SET_VALUE, 109 SOF_CTRL_TYPE_VALUE_CHAN_GET, 110 SOF_CTRL_CMD_VOLUME, 111 true); 112 113 pm_runtime_mark_last_busy(sdev->dev); 114 err = pm_runtime_put_autosuspend(sdev->dev); 115 if (err < 0) 116 dev_err_ratelimited(sdev->dev, 117 "error: volume put failed to idle %d\n", 118 err); 119 return 0; 120 } 121 122 int snd_sof_switch_get(struct snd_kcontrol *kcontrol, 123 struct snd_ctl_elem_value *ucontrol) 124 { 125 struct soc_mixer_control *sm = 126 (struct soc_mixer_control *)kcontrol->private_value; 127 struct snd_sof_control *scontrol = sm->dobj.private; 128 struct snd_sof_dev *sdev = scontrol->sdev; 129 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 130 unsigned int i, channels = scontrol->num_channels; 131 int err, ret; 132 133 ret = pm_runtime_get_sync(sdev->dev); 134 if (ret < 0) { 135 dev_err_ratelimited(sdev->dev, 136 "error: switch get failed to resume %d\n", 137 ret); 138 pm_runtime_put_noidle(sdev->dev); 139 return ret; 140 } 141 142 /* get all the mixer data from DSP */ 143 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 144 SOF_IPC_COMP_GET_VALUE, 145 SOF_CTRL_TYPE_VALUE_CHAN_GET, 146 SOF_CTRL_CMD_SWITCH, 147 false); 148 149 /* read back each channel */ 150 for (i = 0; i < channels; i++) 151 ucontrol->value.integer.value[i] = cdata->chanv[i].value; 152 153 pm_runtime_mark_last_busy(sdev->dev); 154 err = pm_runtime_put_autosuspend(sdev->dev); 155 if (err < 0) 156 dev_err_ratelimited(sdev->dev, 157 "error: switch get failed to idle %d\n", 158 err); 159 return 0; 160 } 161 162 int snd_sof_switch_put(struct snd_kcontrol *kcontrol, 163 struct snd_ctl_elem_value *ucontrol) 164 { 165 struct soc_mixer_control *sm = 166 (struct soc_mixer_control *)kcontrol->private_value; 167 struct snd_sof_control *scontrol = sm->dobj.private; 168 struct snd_sof_dev *sdev = scontrol->sdev; 169 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 170 unsigned int i, channels = scontrol->num_channels; 171 int ret, err; 172 173 ret = pm_runtime_get_sync(sdev->dev); 174 if (ret < 0) { 175 dev_err_ratelimited(sdev->dev, 176 "error: switch put failed to resume %d\n", 177 ret); 178 pm_runtime_put_noidle(sdev->dev); 179 return ret; 180 } 181 182 /* update each channel */ 183 for (i = 0; i < channels; i++) { 184 cdata->chanv[i].value = ucontrol->value.integer.value[i]; 185 cdata->chanv[i].channel = i; 186 } 187 188 /* notify DSP of mixer updates */ 189 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 190 SOF_IPC_COMP_SET_VALUE, 191 SOF_CTRL_TYPE_VALUE_CHAN_GET, 192 SOF_CTRL_CMD_SWITCH, 193 true); 194 195 pm_runtime_mark_last_busy(sdev->dev); 196 err = pm_runtime_put_autosuspend(sdev->dev); 197 if (err < 0) 198 dev_err_ratelimited(sdev->dev, 199 "error: switch put failed to idle %d\n", 200 err); 201 return 0; 202 } 203 204 int snd_sof_enum_get(struct snd_kcontrol *kcontrol, 205 struct snd_ctl_elem_value *ucontrol) 206 { 207 struct soc_enum *se = 208 (struct soc_enum *)kcontrol->private_value; 209 struct snd_sof_control *scontrol = se->dobj.private; 210 struct snd_sof_dev *sdev = scontrol->sdev; 211 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 212 unsigned int i, channels = scontrol->num_channels; 213 int err, ret; 214 215 ret = pm_runtime_get_sync(sdev->dev); 216 if (ret < 0) { 217 dev_err_ratelimited(sdev->dev, 218 "error: enum get failed to resume %d\n", 219 ret); 220 pm_runtime_put_noidle(sdev->dev); 221 return ret; 222 } 223 224 /* get all the enum data from DSP */ 225 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 226 SOF_IPC_COMP_GET_VALUE, 227 SOF_CTRL_TYPE_VALUE_CHAN_GET, 228 SOF_CTRL_CMD_ENUM, 229 false); 230 231 /* read back each channel */ 232 for (i = 0; i < channels; i++) 233 ucontrol->value.enumerated.item[i] = cdata->chanv[i].value; 234 235 pm_runtime_mark_last_busy(sdev->dev); 236 err = pm_runtime_put_autosuspend(sdev->dev); 237 if (err < 0) 238 dev_err_ratelimited(sdev->dev, 239 "error: enum get failed to idle %d\n", 240 err); 241 return 0; 242 } 243 244 int snd_sof_enum_put(struct snd_kcontrol *kcontrol, 245 struct snd_ctl_elem_value *ucontrol) 246 { 247 struct soc_enum *se = 248 (struct soc_enum *)kcontrol->private_value; 249 struct snd_sof_control *scontrol = se->dobj.private; 250 struct snd_sof_dev *sdev = scontrol->sdev; 251 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 252 unsigned int i, channels = scontrol->num_channels; 253 int ret, err; 254 255 ret = pm_runtime_get_sync(sdev->dev); 256 if (ret < 0) { 257 dev_err_ratelimited(sdev->dev, 258 "error: enum put failed to resume %d\n", 259 ret); 260 pm_runtime_put_noidle(sdev->dev); 261 return ret; 262 } 263 264 /* update each channel */ 265 for (i = 0; i < channels; i++) { 266 cdata->chanv[i].value = ucontrol->value.enumerated.item[i]; 267 cdata->chanv[i].channel = i; 268 } 269 270 /* notify DSP of enum updates */ 271 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 272 SOF_IPC_COMP_SET_VALUE, 273 SOF_CTRL_TYPE_VALUE_CHAN_GET, 274 SOF_CTRL_CMD_ENUM, 275 true); 276 277 pm_runtime_mark_last_busy(sdev->dev); 278 err = pm_runtime_put_autosuspend(sdev->dev); 279 if (err < 0) 280 dev_err_ratelimited(sdev->dev, 281 "error: enum put failed to idle %d\n", 282 err); 283 return 0; 284 } 285 286 int snd_sof_bytes_get(struct snd_kcontrol *kcontrol, 287 struct snd_ctl_elem_value *ucontrol) 288 { 289 struct soc_bytes_ext *be = 290 (struct soc_bytes_ext *)kcontrol->private_value; 291 struct snd_sof_control *scontrol = be->dobj.private; 292 struct snd_sof_dev *sdev = scontrol->sdev; 293 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 294 struct sof_abi_hdr *data = cdata->data; 295 size_t size; 296 int ret, err; 297 298 if (be->max > sizeof(ucontrol->value.bytes.data)) { 299 dev_err_ratelimited(sdev->dev, 300 "error: data max %d exceeds ucontrol data array size\n", 301 be->max); 302 return -EINVAL; 303 } 304 305 ret = pm_runtime_get_sync(sdev->dev); 306 if (ret < 0) { 307 dev_err_ratelimited(sdev->dev, 308 "error: bytes get failed to resume %d\n", 309 ret); 310 pm_runtime_put_noidle(sdev->dev); 311 return ret; 312 } 313 314 /* get all the binary data from DSP */ 315 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 316 SOF_IPC_COMP_GET_DATA, 317 SOF_CTRL_TYPE_DATA_GET, 318 scontrol->cmd, 319 false); 320 321 size = data->size + sizeof(*data); 322 if (size > be->max) { 323 dev_err_ratelimited(sdev->dev, 324 "error: DSP sent %zu bytes max is %d\n", 325 size, be->max); 326 ret = -EINVAL; 327 goto out; 328 } 329 330 /* copy back to kcontrol */ 331 memcpy(ucontrol->value.bytes.data, data, size); 332 333 out: 334 pm_runtime_mark_last_busy(sdev->dev); 335 err = pm_runtime_put_autosuspend(sdev->dev); 336 if (err < 0) 337 dev_err_ratelimited(sdev->dev, 338 "error: bytes get failed to idle %d\n", 339 err); 340 return ret; 341 } 342 343 int snd_sof_bytes_put(struct snd_kcontrol *kcontrol, 344 struct snd_ctl_elem_value *ucontrol) 345 { 346 struct soc_bytes_ext *be = 347 (struct soc_bytes_ext *)kcontrol->private_value; 348 struct snd_sof_control *scontrol = be->dobj.private; 349 struct snd_sof_dev *sdev = scontrol->sdev; 350 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 351 struct sof_abi_hdr *data = cdata->data; 352 int ret, err; 353 354 if (be->max > sizeof(ucontrol->value.bytes.data)) { 355 dev_err_ratelimited(sdev->dev, 356 "error: data max %d exceeds ucontrol data array size\n", 357 be->max); 358 return -EINVAL; 359 } 360 361 if (data->size > be->max) { 362 dev_err_ratelimited(sdev->dev, 363 "error: size too big %d bytes max is %d\n", 364 data->size, be->max); 365 return -EINVAL; 366 } 367 368 ret = pm_runtime_get_sync(sdev->dev); 369 if (ret < 0) { 370 dev_err_ratelimited(sdev->dev, 371 "error: bytes put failed to resume %d\n", 372 ret); 373 pm_runtime_put_noidle(sdev->dev); 374 return ret; 375 } 376 377 /* copy from kcontrol */ 378 memcpy(data, ucontrol->value.bytes.data, data->size); 379 380 /* notify DSP of byte control updates */ 381 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 382 SOF_IPC_COMP_SET_DATA, 383 SOF_CTRL_TYPE_DATA_SET, 384 scontrol->cmd, 385 true); 386 387 pm_runtime_mark_last_busy(sdev->dev); 388 err = pm_runtime_put_autosuspend(sdev->dev); 389 if (err < 0) 390 dev_err_ratelimited(sdev->dev, 391 "error: bytes put failed to idle %d\n", 392 err); 393 return ret; 394 } 395 396 int snd_sof_bytes_ext_put(struct snd_kcontrol *kcontrol, 397 const unsigned int __user *binary_data, 398 unsigned int size) 399 { 400 struct soc_bytes_ext *be = 401 (struct soc_bytes_ext *)kcontrol->private_value; 402 struct snd_sof_control *scontrol = be->dobj.private; 403 struct snd_sof_dev *sdev = scontrol->sdev; 404 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 405 struct snd_ctl_tlv header; 406 const struct snd_ctl_tlv __user *tlvd = 407 (const struct snd_ctl_tlv __user *)binary_data; 408 int ret; 409 int err; 410 411 /* 412 * The beginning of bytes data contains a header from where 413 * the length (as bytes) is needed to know the correct copy 414 * length of data from tlvd->tlv. 415 */ 416 if (copy_from_user(&header, tlvd, sizeof(const struct snd_ctl_tlv))) 417 return -EFAULT; 418 419 /* be->max is coming from topology */ 420 if (header.length > be->max) { 421 dev_err_ratelimited(sdev->dev, "error: Bytes data size %d exceeds max %d.\n", 422 header.length, be->max); 423 return -EINVAL; 424 } 425 426 /* Check that header id matches the command */ 427 if (header.numid != scontrol->cmd) { 428 dev_err_ratelimited(sdev->dev, 429 "error: incorrect numid %d\n", 430 header.numid); 431 return -EINVAL; 432 } 433 434 if (copy_from_user(cdata->data, tlvd->tlv, header.length)) 435 return -EFAULT; 436 437 if (cdata->data->magic != SOF_ABI_MAGIC) { 438 dev_err_ratelimited(sdev->dev, 439 "error: Wrong ABI magic 0x%08x.\n", 440 cdata->data->magic); 441 return -EINVAL; 442 } 443 444 if (SOF_ABI_VERSION_INCOMPATIBLE(SOF_ABI_VERSION, cdata->data->abi)) { 445 dev_err_ratelimited(sdev->dev, "error: Incompatible ABI version 0x%08x.\n", 446 cdata->data->abi); 447 return -EINVAL; 448 } 449 450 if (cdata->data->size + sizeof(const struct sof_abi_hdr) > be->max) { 451 dev_err_ratelimited(sdev->dev, "error: Mismatch in ABI data size (truncated?).\n"); 452 return -EINVAL; 453 } 454 455 ret = pm_runtime_get_sync(sdev->dev); 456 if (ret < 0) { 457 dev_err_ratelimited(sdev->dev, 458 "error: bytes_ext put failed to resume %d\n", 459 ret); 460 pm_runtime_put_noidle(sdev->dev); 461 return ret; 462 } 463 464 /* notify DSP of byte control updates */ 465 snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 466 SOF_IPC_COMP_SET_DATA, 467 SOF_CTRL_TYPE_DATA_SET, 468 scontrol->cmd, 469 true); 470 471 pm_runtime_mark_last_busy(sdev->dev); 472 err = pm_runtime_put_autosuspend(sdev->dev); 473 if (err < 0) 474 dev_err_ratelimited(sdev->dev, 475 "error: bytes_ext put failed to idle %d\n", 476 err); 477 478 return ret; 479 } 480 481 int snd_sof_bytes_ext_get(struct snd_kcontrol *kcontrol, 482 unsigned int __user *binary_data, 483 unsigned int size) 484 { 485 struct soc_bytes_ext *be = 486 (struct soc_bytes_ext *)kcontrol->private_value; 487 struct snd_sof_control *scontrol = be->dobj.private; 488 struct snd_sof_dev *sdev = scontrol->sdev; 489 struct sof_ipc_ctrl_data *cdata = scontrol->control_data; 490 struct snd_ctl_tlv header; 491 struct snd_ctl_tlv __user *tlvd = 492 (struct snd_ctl_tlv __user *)binary_data; 493 int data_size; 494 int err; 495 int ret; 496 497 ret = pm_runtime_get_sync(sdev->dev); 498 if (ret < 0) { 499 dev_err_ratelimited(sdev->dev, 500 "error: bytes_ext get failed to resume %d\n", 501 ret); 502 pm_runtime_put_noidle(sdev->dev); 503 return ret; 504 } 505 506 /* 507 * Decrement the limit by ext bytes header size to 508 * ensure the user space buffer is not exceeded. 509 */ 510 size -= sizeof(const struct snd_ctl_tlv); 511 512 /* set the ABI header values */ 513 cdata->data->magic = SOF_ABI_MAGIC; 514 cdata->data->abi = SOF_ABI_VERSION; 515 516 /* get all the component data from DSP */ 517 ret = snd_sof_ipc_set_get_comp_data(sdev->ipc, scontrol, 518 SOF_IPC_COMP_GET_DATA, 519 SOF_CTRL_TYPE_DATA_GET, 520 scontrol->cmd, 521 false); 522 523 /* Prevent read of other kernel data or possibly corrupt response */ 524 data_size = cdata->data->size + sizeof(const struct sof_abi_hdr); 525 526 /* check data size doesn't exceed max coming from topology */ 527 if (data_size > be->max) { 528 dev_err_ratelimited(sdev->dev, "error: user data size %d exceeds max size %d.\n", 529 data_size, be->max); 530 ret = -EINVAL; 531 goto out; 532 } 533 534 header.numid = scontrol->cmd; 535 header.length = data_size; 536 if (copy_to_user(tlvd, &header, sizeof(const struct snd_ctl_tlv))) { 537 ret = -EFAULT; 538 goto out; 539 } 540 541 if (copy_to_user(tlvd->tlv, cdata->data, data_size)) 542 ret = -EFAULT; 543 544 out: 545 pm_runtime_mark_last_busy(sdev->dev); 546 err = pm_runtime_put_autosuspend(sdev->dev); 547 if (err < 0) 548 dev_err_ratelimited(sdev->dev, 549 "error: bytes_ext get failed to idle %d\n", 550 err); 551 return ret; 552 } 553