1// SPDX-License-Identifier: GPL-2.0+ 2// 3// soc-dapm.c -- ALSA SoC Dynamic Audio Power Management 4// 5// Copyright 2005 Wolfson Microelectronics PLC. 6// Author: Liam Girdwood <lrg@slimlogic.co.uk> 7// 8// Features: 9// o Changes power status of internal codec blocks depending on the 10// dynamic configuration of codec internal audio paths and active 11// DACs/ADCs. 12// o Platform power domain - can support external components i.e. amps and 13// mic/headphone insertion events. 14// o Automatic Mic Bias support 15// o Jack insertion power event initiation - e.g. hp insertion will enable 16// sinks, dacs, etc 17// o Delayed power down of audio subsystem to reduce pops between a quick 18// device reopen. 19 20#include <linux/module.h> 21#include <linux/init.h> 22#include <linux/async.h> 23#include <linux/delay.h> 24#include <linux/pm.h> 25#include <linux/bitops.h> 26#include <linux/platform_device.h> 27#include <linux/jiffies.h> 28#include <linux/debugfs.h> 29#include <linux/pm_runtime.h> 30#include <linux/regulator/consumer.h> 31#include <linux/pinctrl/consumer.h> 32#include <linux/clk.h> 33#include <linux/slab.h> 34#include <sound/core.h> 35#include <sound/pcm.h> 36#include <sound/pcm_params.h> 37#include <sound/soc.h> 38#include <sound/initval.h> 39 40#include <trace/events/asoc.h> 41 42#define DAPM_UPDATE_STAT(widget, val) widget->dapm->card->dapm_stats.val++; 43 44#define SND_SOC_DAPM_DIR_REVERSE(x) ((x == SND_SOC_DAPM_DIR_IN) ? \ 45 SND_SOC_DAPM_DIR_OUT : SND_SOC_DAPM_DIR_IN) 46 47#define snd_soc_dapm_for_each_direction(dir) \ 48 for ((dir) = SND_SOC_DAPM_DIR_IN; (dir) <= SND_SOC_DAPM_DIR_OUT; \ 49 (dir)++) 50 51static int snd_soc_dapm_add_path(struct snd_soc_dapm_context *dapm, 52 struct snd_soc_dapm_widget *wsource, struct snd_soc_dapm_widget *wsink, 53 const char *control, 54 int (*connected)(struct snd_soc_dapm_widget *source, 55 struct snd_soc_dapm_widget *sink)); 56 57struct snd_soc_dapm_widget * 58snd_soc_dapm_new_control(struct snd_soc_dapm_context *dapm, 59 const struct snd_soc_dapm_widget *widget); 60 61struct snd_soc_dapm_widget * 62snd_soc_dapm_new_control_unlocked(struct snd_soc_dapm_context *dapm, 63 const struct snd_soc_dapm_widget *widget); 64 65static unsigned int soc_dapm_read(struct snd_soc_dapm_context *dapm, int reg); 66 67/* dapm power sequences - make this per codec in the future */ 68static int dapm_up_seq[] = { 69 [snd_soc_dapm_pre] = 1, 70 [snd_soc_dapm_regulator_supply] = 2, 71 [snd_soc_dapm_pinctrl] = 2, 72 [snd_soc_dapm_clock_supply] = 2, 73 [snd_soc_dapm_supply] = 3, 74 [snd_soc_dapm_micbias] = 4, 75 [snd_soc_dapm_vmid] = 4, 76 [snd_soc_dapm_dai_link] = 3, 77 [snd_soc_dapm_dai_in] = 5, 78 [snd_soc_dapm_dai_out] = 5, 79 [snd_soc_dapm_aif_in] = 5, 80 [snd_soc_dapm_aif_out] = 5, 81 [snd_soc_dapm_mic] = 6, 82 [snd_soc_dapm_siggen] = 6, 83 [snd_soc_dapm_input] = 6, 84 [snd_soc_dapm_output] = 6, 85 [snd_soc_dapm_mux] = 7, 86 [snd_soc_dapm_demux] = 7, 87 [snd_soc_dapm_dac] = 8, 88 [snd_soc_dapm_switch] = 9, 89 [snd_soc_dapm_mixer] = 9, 90 [snd_soc_dapm_mixer_named_ctl] = 9, 91 [snd_soc_dapm_pga] = 10, 92 [snd_soc_dapm_buffer] = 10, 93 [snd_soc_dapm_scheduler] = 10, 94 [snd_soc_dapm_effect] = 10, 95 [snd_soc_dapm_src] = 10, 96 [snd_soc_dapm_asrc] = 10, 97 [snd_soc_dapm_encoder] = 10, 98 [snd_soc_dapm_decoder] = 10, 99 [snd_soc_dapm_adc] = 11, 100 [snd_soc_dapm_out_drv] = 12, 101 [snd_soc_dapm_hp] = 12, 102 [snd_soc_dapm_spk] = 12, 103 [snd_soc_dapm_line] = 12, 104 [snd_soc_dapm_sink] = 12, 105 [snd_soc_dapm_kcontrol] = 13, 106 [snd_soc_dapm_post] = 14, 107}; 108 109static int dapm_down_seq[] = { 110 [snd_soc_dapm_pre] = 1, 111 [snd_soc_dapm_kcontrol] = 2, 112 [snd_soc_dapm_adc] = 3, 113 [snd_soc_dapm_hp] = 4, 114 [snd_soc_dapm_spk] = 4, 115 [snd_soc_dapm_line] = 4, 116 [snd_soc_dapm_out_drv] = 4, 117 [snd_soc_dapm_sink] = 4, 118 [snd_soc_dapm_pga] = 5, 119 [snd_soc_dapm_buffer] = 5, 120 [snd_soc_dapm_scheduler] = 5, 121 [snd_soc_dapm_effect] = 5, 122 [snd_soc_dapm_src] = 5, 123 [snd_soc_dapm_asrc] = 5, 124 [snd_soc_dapm_encoder] = 5, 125 [snd_soc_dapm_decoder] = 5, 126 [snd_soc_dapm_switch] = 6, 127 [snd_soc_dapm_mixer_named_ctl] = 6, 128 [snd_soc_dapm_mixer] = 6, 129 [snd_soc_dapm_dac] = 7, 130 [snd_soc_dapm_mic] = 8, 131 [snd_soc_dapm_siggen] = 8, 132 [snd_soc_dapm_input] = 8, 133 [snd_soc_dapm_output] = 8, 134 [snd_soc_dapm_micbias] = 9, 135 [snd_soc_dapm_vmid] = 9, 136 [snd_soc_dapm_mux] = 10, 137 [snd_soc_dapm_demux] = 10, 138 [snd_soc_dapm_aif_in] = 11, 139 [snd_soc_dapm_aif_out] = 11, 140 [snd_soc_dapm_dai_in] = 11, 141 [snd_soc_dapm_dai_out] = 11, 142 [snd_soc_dapm_dai_link] = 12, 143 [snd_soc_dapm_supply] = 13, 144 [snd_soc_dapm_clock_supply] = 14, 145 [snd_soc_dapm_pinctrl] = 14, 146 [snd_soc_dapm_regulator_supply] = 14, 147 [snd_soc_dapm_post] = 15, 148}; 149 150static void dapm_assert_locked(struct snd_soc_dapm_context *dapm) 151{ 152 if (dapm->card && dapm->card->instantiated) 153 lockdep_assert_held(&dapm->card->dapm_mutex); 154} 155 156static void pop_wait(u32 pop_time) 157{ 158 if (pop_time) 159 schedule_timeout_uninterruptible(msecs_to_jiffies(pop_time)); 160} 161 162__printf(3, 4) 163static void pop_dbg(struct device *dev, u32 pop_time, const char *fmt, ...) 164{ 165 va_list args; 166 char *buf; 167 168 if (!pop_time) 169 return; 170 171 buf = kmalloc(PAGE_SIZE, GFP_KERNEL); 172 if (buf == NULL) 173 return; 174 175 va_start(args, fmt); 176 vsnprintf(buf, PAGE_SIZE, fmt, args); 177 dev_info(dev, "%s", buf); 178 va_end(args); 179 180 kfree(buf); 181} 182 183static bool dapm_dirty_widget(struct snd_soc_dapm_widget *w) 184{ 185 return !list_empty(&w->dirty); 186} 187 188static void dapm_mark_dirty(struct snd_soc_dapm_widget *w, const char *reason) 189{ 190 dapm_assert_locked(w->dapm); 191 192 if (!dapm_dirty_widget(w)) { 193 dev_vdbg(w->dapm->dev, "Marking %s dirty due to %s\n", 194 w->name, reason); 195 list_add_tail(&w->dirty, &w->dapm->card->dapm_dirty); 196 } 197} 198 199/* 200 * Common implementation for dapm_widget_invalidate_input_paths() and 201 * dapm_widget_invalidate_output_paths(). The function is inlined since the 202 * combined size of the two specialized functions is only marginally larger then 203 * the size of the generic function and at the same time the fast path of the 204 * specialized functions is significantly smaller than the generic function. 205 */ 206static __always_inline void dapm_widget_invalidate_paths( 207 struct snd_soc_dapm_widget *w, enum snd_soc_dapm_direction dir) 208{ 209 enum snd_soc_dapm_direction rdir = SND_SOC_DAPM_DIR_REVERSE(dir); 210 struct snd_soc_dapm_widget *node; 211 struct snd_soc_dapm_path *p; 212 LIST_HEAD(list); 213 214 dapm_assert_locked(w->dapm); 215 216 if (w->endpoints[dir] == -1) 217 return; 218 219 list_add_tail(&w->work_list, &list); 220 w->endpoints[dir] = -1; 221 222 list_for_each_entry(w, &list, work_list) { 223 snd_soc_dapm_widget_for_each_path(w, dir, p) { 224 if (p->is_supply || p->weak || !p->connect) 225 continue; 226 node = p->node[rdir]; 227 if (node->endpoints[dir] != -1) { 228 node->endpoints[dir] = -1; 229 list_add_tail(&node->work_list, &list); 230 } 231 } 232 } 233} 234 235/* 236 * dapm_widget_invalidate_input_paths() - Invalidate the cached number of 237 * input paths 238 * @w: The widget for which to invalidate the cached number of input paths 239 * 240 * Resets the cached number of inputs for the specified widget and all widgets 241 * that can be reached via outcoming paths from the widget. 242 * 243 * This function must be called if the number of output paths for a widget might 244 * have changed. E.g. if the source state of a widget changes or a path is added 245 * or activated with the widget as the sink. 246 */ 247static void dapm_widget_invalidate_input_paths(struct snd_soc_dapm_widget *w) 248{ 249 dapm_widget_invalidate_paths(w, SND_SOC_DAPM_DIR_IN); 250} 251 252/* 253 * dapm_widget_invalidate_output_paths() - Invalidate the cached number of 254 * output paths 255 * @w: The widget for which to invalidate the cached number of output paths 256 * 257 * Resets the cached number of outputs for the specified widget and all widgets 258 * that can be reached via incoming paths from the widget. 259 * 260 * This function must be called if the number of output paths for a widget might 261 * have changed. E.g. if the sink state of a widget changes or a path is added 262 * or activated with the widget as the source. 263 */ 264static void dapm_widget_invalidate_output_paths(struct snd_soc_dapm_widget *w) 265{ 266 dapm_widget_invalidate_paths(w, SND_SOC_DAPM_DIR_OUT); 267} 268 269/* 270 * dapm_path_invalidate() - Invalidates the cached number of inputs and outputs 271 * for the widgets connected to a path 272 * @p: The path to invalidate 273 * 274 * Resets the cached number of inputs for the sink of the path and the cached 275 * number of outputs for the source of the path. 276 * 277 * This function must be called when a path is added, removed or the connected 278 * state changes. 279 */ 280static void dapm_path_invalidate(struct snd_soc_dapm_path *p) 281{ 282 /* 283 * Weak paths or supply paths do not influence the number of input or 284 * output paths of their neighbors. 285 */ 286 if (p->weak || p->is_supply) 287 return; 288 289 /* 290 * The number of connected endpoints is the sum of the number of 291 * connected endpoints of all neighbors. If a node with 0 connected 292 * endpoints is either connected or disconnected that sum won't change, 293 * so there is no need to re-check the path. 294 */ 295 if (p->source->endpoints[SND_SOC_DAPM_DIR_IN] != 0) 296 dapm_widget_invalidate_input_paths(p->sink); 297 if (p->sink->endpoints[SND_SOC_DAPM_DIR_OUT] != 0) 298 dapm_widget_invalidate_output_paths(p->source); 299} 300 301void dapm_mark_endpoints_dirty(struct snd_soc_card *card) 302{ 303 struct snd_soc_dapm_widget *w; 304 305 mutex_lock(&card->dapm_mutex); 306 307 for_each_card_widgets(card, w) { 308 if (w->is_ep) { 309 dapm_mark_dirty(w, "Rechecking endpoints"); 310 if (w->is_ep & SND_SOC_DAPM_EP_SINK) 311 dapm_widget_invalidate_output_paths(w); 312 if (w->is_ep & SND_SOC_DAPM_EP_SOURCE) 313 dapm_widget_invalidate_input_paths(w); 314 } 315 } 316 317 mutex_unlock(&card->dapm_mutex); 318} 319EXPORT_SYMBOL_GPL(dapm_mark_endpoints_dirty); 320 321/* create a new dapm widget */ 322static inline struct snd_soc_dapm_widget *dapm_cnew_widget( 323 const struct snd_soc_dapm_widget *_widget) 324{ 325 struct snd_soc_dapm_widget *w; 326 327 w = kmemdup(_widget, sizeof(*_widget), GFP_KERNEL); 328 if (!w) 329 return NULL; 330 331 /* 332 * w->name is duplicated in caller, but w->sname isn't. 333 * Duplicate it here if defined 334 */ 335 if (_widget->sname) { 336 w->sname = kstrdup_const(_widget->sname, GFP_KERNEL); 337 if (!w->sname) { 338 kfree(w); 339 return NULL; 340 } 341 } 342 return w; 343} 344 345struct dapm_kcontrol_data { 346 unsigned int value; 347 struct snd_soc_dapm_widget *widget; 348 struct list_head paths; 349 struct snd_soc_dapm_widget_list *wlist; 350}; 351 352static int dapm_kcontrol_data_alloc(struct snd_soc_dapm_widget *widget, 353 struct snd_kcontrol *kcontrol, const char *ctrl_name) 354{ 355 struct dapm_kcontrol_data *data; 356 struct soc_mixer_control *mc; 357 struct soc_enum *e; 358 const char *name; 359 int ret; 360 361 data = kzalloc(sizeof(*data), GFP_KERNEL); 362 if (!data) 363 return -ENOMEM; 364 365 INIT_LIST_HEAD(&data->paths); 366 367 switch (widget->id) { 368 case snd_soc_dapm_switch: 369 case snd_soc_dapm_mixer: 370 case snd_soc_dapm_mixer_named_ctl: 371 mc = (struct soc_mixer_control *)kcontrol->private_value; 372 373 if (mc->autodisable && snd_soc_volsw_is_stereo(mc)) 374 dev_warn(widget->dapm->dev, 375 "ASoC: Unsupported stereo autodisable control '%s'\n", 376 ctrl_name); 377 378 if (mc->autodisable) { 379 struct snd_soc_dapm_widget template; 380 381 name = kasprintf(GFP_KERNEL, "%s %s", ctrl_name, 382 "Autodisable"); 383 if (!name) { 384 ret = -ENOMEM; 385 goto err_data; 386 } 387 388 memset(&template, 0, sizeof(template)); 389 template.reg = mc->reg; 390 template.mask = (1 << fls(mc->max)) - 1; 391 template.shift = mc->shift; 392 if (mc->invert) 393 template.off_val = mc->max; 394 else 395 template.off_val = 0; 396 template.on_val = template.off_val; 397 template.id = snd_soc_dapm_kcontrol; 398 template.name = name; 399 400 data->value = template.on_val; 401 402 data->widget = 403 snd_soc_dapm_new_control_unlocked(widget->dapm, 404 &template); 405 kfree(name); 406 if (IS_ERR(data->widget)) { 407 ret = PTR_ERR(data->widget); 408 goto err_data; 409 } 410 } 411 break; 412 case snd_soc_dapm_demux: 413 case snd_soc_dapm_mux: 414 e = (struct soc_enum *)kcontrol->private_value; 415 416 if (e->autodisable) { 417 struct snd_soc_dapm_widget template; 418 419 name = kasprintf(GFP_KERNEL, "%s %s", ctrl_name, 420 "Autodisable"); 421 if (!name) { 422 ret = -ENOMEM; 423 goto err_data; 424 } 425 426 memset(&template, 0, sizeof(template)); 427 template.reg = e->reg; 428 template.mask = e->mask; 429 template.shift = e->shift_l; 430 template.off_val = snd_soc_enum_item_to_val(e, 0); 431 template.on_val = template.off_val; 432 template.id = snd_soc_dapm_kcontrol; 433 template.name = name; 434 435 data->value = template.on_val; 436 437 data->widget = snd_soc_dapm_new_control_unlocked( 438 widget->dapm, &template); 439 kfree(name); 440 if (IS_ERR(data->widget)) { 441 ret = PTR_ERR(data->widget); 442 goto err_data; 443 } 444 445 snd_soc_dapm_add_path(widget->dapm, data->widget, 446 widget, NULL, NULL); 447 } else if (e->reg != SND_SOC_NOPM) { 448 data->value = soc_dapm_read(widget->dapm, e->reg) & 449 (e->mask << e->shift_l); 450 } 451 break; 452 default: 453 break; 454 } 455 456 kcontrol->private_data = data; 457 458 return 0; 459 460err_data: 461 kfree(data); 462 return ret; 463} 464 465static void dapm_kcontrol_free(struct snd_kcontrol *kctl) 466{ 467 struct dapm_kcontrol_data *data = snd_kcontrol_chip(kctl); 468 469 list_del(&data->paths); 470 kfree(data->wlist); 471 kfree(data); 472} 473 474static struct snd_soc_dapm_widget_list *dapm_kcontrol_get_wlist( 475 const struct snd_kcontrol *kcontrol) 476{ 477 struct dapm_kcontrol_data *data = snd_kcontrol_chip(kcontrol); 478 479 return data->wlist; 480} 481 482static int dapm_kcontrol_add_widget(struct snd_kcontrol *kcontrol, 483 struct snd_soc_dapm_widget *widget) 484{ 485 struct dapm_kcontrol_data *data = snd_kcontrol_chip(kcontrol); 486 struct snd_soc_dapm_widget_list *new_wlist; 487 unsigned int n; 488 489 if (data->wlist) 490 n = data->wlist->num_widgets + 1; 491 else 492 n = 1; 493 494 new_wlist = krealloc(data->wlist, 495 struct_size(new_wlist, widgets, n), 496 GFP_KERNEL); 497 if (!new_wlist) 498 return -ENOMEM; 499 500 new_wlist->widgets[n - 1] = widget; 501 new_wlist->num_widgets = n; 502 503 data->wlist = new_wlist; 504 505 return 0; 506} 507 508static void dapm_kcontrol_add_path(const struct snd_kcontrol *kcontrol, 509 struct snd_soc_dapm_path *path) 510{ 511 struct dapm_kcontrol_data *data = snd_kcontrol_chip(kcontrol); 512 513 list_add_tail(&path->list_kcontrol, &data->paths); 514} 515 516static bool dapm_kcontrol_is_powered(const struct snd_kcontrol *kcontrol) 517{ 518 struct dapm_kcontrol_data *data = snd_kcontrol_chip(kcontrol); 519 520 if (!data->widget) 521 return true; 522 523 return data->widget->power; 524} 525 526static struct list_head *dapm_kcontrol_get_path_list( 527 const struct snd_kcontrol *kcontrol) 528{ 529 struct dapm_kcontrol_data *data = snd_kcontrol_chip(kcontrol); 530 531 return &data->paths; 532} 533 534#define dapm_kcontrol_for_each_path(path, kcontrol) \ 535 list_for_each_entry(path, dapm_kcontrol_get_path_list(kcontrol), \ 536 list_kcontrol) 537 538unsigned int dapm_kcontrol_get_value(const struct snd_kcontrol *kcontrol) 539{ 540 struct dapm_kcontrol_data *data = snd_kcontrol_chip(kcontrol); 541 542 return data->value; 543} 544EXPORT_SYMBOL_GPL(dapm_kcontrol_get_value); 545 546static bool dapm_kcontrol_set_value(const struct snd_kcontrol *kcontrol, 547 unsigned int value) 548{ 549 struct dapm_kcontrol_data *data = snd_kcontrol_chip(kcontrol); 550 551 if (data->value == value) 552 return false; 553 554 if (data->widget) { 555 switch (dapm_kcontrol_get_wlist(kcontrol)->widgets[0]->id) { 556 case snd_soc_dapm_switch: 557 case snd_soc_dapm_mixer: 558 case snd_soc_dapm_mixer_named_ctl: 559 data->widget->on_val = value & data->widget->mask; 560 break; 561 case snd_soc_dapm_demux: 562 case snd_soc_dapm_mux: 563 data->widget->on_val = value >> data->widget->shift; 564 break; 565 default: 566 data->widget->on_val = value; 567 break; 568 } 569 } 570 571 data->value = value; 572 573 return true; 574} 575 576/** 577 * snd_soc_dapm_kcontrol_widget() - Returns the widget associated to a 578 * kcontrol 579 * @kcontrol: The kcontrol 580 */ 581struct snd_soc_dapm_widget *snd_soc_dapm_kcontrol_widget( 582 struct snd_kcontrol *kcontrol) 583{ 584 return dapm_kcontrol_get_wlist(kcontrol)->widgets[0]; 585} 586EXPORT_SYMBOL_GPL(snd_soc_dapm_kcontrol_widget); 587 588/** 589 * snd_soc_dapm_kcontrol_dapm() - Returns the dapm context associated to a 590 * kcontrol 591 * @kcontrol: The kcontrol 592 * 593 * Note: This function must only be used on kcontrols that are known to have 594 * been registered for a CODEC. Otherwise the behaviour is undefined. 595 */ 596struct snd_soc_dapm_context *snd_soc_dapm_kcontrol_dapm( 597 struct snd_kcontrol *kcontrol) 598{ 599 return dapm_kcontrol_get_wlist(kcontrol)->widgets[0]->dapm; 600} 601EXPORT_SYMBOL_GPL(snd_soc_dapm_kcontrol_dapm); 602 603static void dapm_reset(struct snd_soc_card *card) 604{ 605 struct snd_soc_dapm_widget *w; 606 607 lockdep_assert_held(&card->dapm_mutex); 608 609 memset(&card->dapm_stats, 0, sizeof(card->dapm_stats)); 610 611 for_each_card_widgets(card, w) { 612 w->new_power = w->power; 613 w->power_checked = false; 614 } 615} 616 617static const char *soc_dapm_prefix(struct snd_soc_dapm_context *dapm) 618{ 619 if (!dapm->component) 620 return NULL; 621 return dapm->component->name_prefix; 622} 623 624static unsigned int soc_dapm_read(struct snd_soc_dapm_context *dapm, int reg) 625{ 626 if (!dapm->component) 627 return -EIO; 628 return snd_soc_component_read(dapm->component, reg); 629} 630 631static int soc_dapm_update_bits(struct snd_soc_dapm_context *dapm, 632 int reg, unsigned int mask, unsigned int value) 633{ 634 if (!dapm->component) 635 return -EIO; 636 return snd_soc_component_update_bits(dapm->component, reg, 637 mask, value); 638} 639 640static int soc_dapm_test_bits(struct snd_soc_dapm_context *dapm, 641 int reg, unsigned int mask, unsigned int value) 642{ 643 if (!dapm->component) 644 return -EIO; 645 return snd_soc_component_test_bits(dapm->component, reg, mask, value); 646} 647 648static void soc_dapm_async_complete(struct snd_soc_dapm_context *dapm) 649{ 650 if (dapm->component) 651 snd_soc_component_async_complete(dapm->component); 652} 653 654static struct snd_soc_dapm_widget * 655dapm_wcache_lookup(struct snd_soc_dapm_wcache *wcache, const char *name) 656{ 657 struct snd_soc_dapm_widget *w = wcache->widget; 658 struct list_head *wlist; 659 const int depth = 2; 660 int i = 0; 661 662 if (w) { 663 wlist = &w->dapm->card->widgets; 664 665 list_for_each_entry_from(w, wlist, list) { 666 if (!strcmp(name, w->name)) 667 return w; 668 669 if (++i == depth) 670 break; 671 } 672 } 673 674 return NULL; 675} 676 677static inline void dapm_wcache_update(struct snd_soc_dapm_wcache *wcache, 678 struct snd_soc_dapm_widget *w) 679{ 680 wcache->widget = w; 681} 682 683/** 684 * snd_soc_dapm_force_bias_level() - Sets the DAPM bias level 685 * @dapm: The DAPM context for which to set the level 686 * @level: The level to set 687 * 688 * Forces the DAPM bias level to a specific state. It will call the bias level 689 * callback of DAPM context with the specified level. This will even happen if 690 * the context is already at the same level. Furthermore it will not go through 691 * the normal bias level sequencing, meaning any intermediate states between the 692 * current and the target state will not be entered. 693 * 694 * Note that the change in bias level is only temporary and the next time 695 * snd_soc_dapm_sync() is called the state will be set to the level as 696 * determined by the DAPM core. The function is mainly intended to be used to 697 * used during probe or resume from suspend to power up the device so 698 * initialization can be done, before the DAPM core takes over. 699 */ 700int snd_soc_dapm_force_bias_level(struct snd_soc_dapm_context *dapm, 701 enum snd_soc_bias_level level) 702{ 703 int ret = 0; 704 705 if (dapm->component) 706 ret = snd_soc_component_set_bias_level(dapm->component, level); 707 708 if (ret == 0) 709 dapm->bias_level = level; 710 711 return ret; 712} 713EXPORT_SYMBOL_GPL(snd_soc_dapm_force_bias_level); 714 715/** 716 * snd_soc_dapm_set_bias_level - set the bias level for the system 717 * @dapm: DAPM context 718 * @level: level to configure 719 * 720 * Configure the bias (power) levels for the SoC audio device. 721 * 722 * Returns 0 for success else error. 723 */ 724static int snd_soc_dapm_set_bias_level(struct snd_soc_dapm_context *dapm, 725 enum snd_soc_bias_level level) 726{ 727 struct snd_soc_card *card = dapm->card; 728 int ret = 0; 729 730 trace_snd_soc_bias_level_start(card, level); 731 732 ret = snd_soc_card_set_bias_level(card, dapm, level); 733 if (ret != 0) 734 goto out; 735 736 if (!card || dapm != &card->dapm) 737 ret = snd_soc_dapm_force_bias_level(dapm, level); 738 739 if (ret != 0) 740 goto out; 741 742 ret = snd_soc_card_set_bias_level_post(card, dapm, level); 743out: 744 trace_snd_soc_bias_level_done(card, level); 745 746 return ret; 747} 748 749/* connect mux widget to its interconnecting audio paths */ 750static int dapm_connect_mux(struct snd_soc_dapm_context *dapm, 751 struct snd_soc_dapm_path *path, const char *control_name, 752 struct snd_soc_dapm_widget *w) 753{ 754 const struct snd_kcontrol_new *kcontrol = &w->kcontrol_news[0]; 755 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 756 unsigned int val, item; 757 int i; 758 759 if (e->reg != SND_SOC_NOPM) { 760 val = soc_dapm_read(dapm, e->reg); 761 val = (val >> e->shift_l) & e->mask; 762 item = snd_soc_enum_val_to_item(e, val); 763 } else { 764 /* since a virtual mux has no backing registers to 765 * decide which path to connect, it will try to match 766 * with the first enumeration. This is to ensure 767 * that the default mux choice (the first) will be 768 * correctly powered up during initialization. 769 */ 770 item = 0; 771 } 772 773 i = match_string(e->texts, e->items, control_name); 774 if (i < 0) 775 return -ENODEV; 776 777 path->name = e->texts[i]; 778 path->connect = (i == item); 779 return 0; 780 781} 782 783/* set up initial codec paths */ 784static void dapm_set_mixer_path_status(struct snd_soc_dapm_path *p, int i, 785 int nth_path) 786{ 787 struct soc_mixer_control *mc = (struct soc_mixer_control *) 788 p->sink->kcontrol_news[i].private_value; 789 unsigned int reg = mc->reg; 790 unsigned int shift = mc->shift; 791 unsigned int max = mc->max; 792 unsigned int mask = (1 << fls(max)) - 1; 793 unsigned int invert = mc->invert; 794 unsigned int val; 795 796 if (reg != SND_SOC_NOPM) { 797 val = soc_dapm_read(p->sink->dapm, reg); 798 /* 799 * The nth_path argument allows this function to know 800 * which path of a kcontrol it is setting the initial 801 * status for. Ideally this would support any number 802 * of paths and channels. But since kcontrols only come 803 * in mono and stereo variants, we are limited to 2 804 * channels. 805 * 806 * The following code assumes for stereo controls the 807 * first path is the left channel, and all remaining 808 * paths are the right channel. 809 */ 810 if (snd_soc_volsw_is_stereo(mc) && nth_path > 0) { 811 if (reg != mc->rreg) 812 val = soc_dapm_read(p->sink->dapm, mc->rreg); 813 val = (val >> mc->rshift) & mask; 814 } else { 815 val = (val >> shift) & mask; 816 } 817 if (invert) 818 val = max - val; 819 p->connect = !!val; 820 } else { 821 /* since a virtual mixer has no backing registers to 822 * decide which path to connect, it will try to match 823 * with initial state. This is to ensure 824 * that the default mixer choice will be 825 * correctly powered up during initialization. 826 */ 827 p->connect = invert; 828 } 829} 830 831/* connect mixer widget to its interconnecting audio paths */ 832static int dapm_connect_mixer(struct snd_soc_dapm_context *dapm, 833 struct snd_soc_dapm_path *path, const char *control_name) 834{ 835 int i, nth_path = 0; 836 837 /* search for mixer kcontrol */ 838 for (i = 0; i < path->sink->num_kcontrols; i++) { 839 if (!strcmp(control_name, path->sink->kcontrol_news[i].name)) { 840 path->name = path->sink->kcontrol_news[i].name; 841 dapm_set_mixer_path_status(path, i, nth_path++); 842 return 0; 843 } 844 } 845 return -ENODEV; 846} 847 848static int dapm_is_shared_kcontrol(struct snd_soc_dapm_context *dapm, 849 struct snd_soc_dapm_widget *kcontrolw, 850 const struct snd_kcontrol_new *kcontrol_new, 851 struct snd_kcontrol **kcontrol) 852{ 853 struct snd_soc_dapm_widget *w; 854 int i; 855 856 *kcontrol = NULL; 857 858 for_each_card_widgets(dapm->card, w) { 859 if (w == kcontrolw || w->dapm != kcontrolw->dapm) 860 continue; 861 for (i = 0; i < w->num_kcontrols; i++) { 862 if (&w->kcontrol_news[i] == kcontrol_new) { 863 if (w->kcontrols) 864 *kcontrol = w->kcontrols[i]; 865 return 1; 866 } 867 } 868 } 869 870 return 0; 871} 872 873/* 874 * Determine if a kcontrol is shared. If it is, look it up. If it isn't, 875 * create it. Either way, add the widget into the control's widget list 876 */ 877static int dapm_create_or_share_kcontrol(struct snd_soc_dapm_widget *w, 878 int kci) 879{ 880 struct snd_soc_dapm_context *dapm = w->dapm; 881 struct snd_card *card = dapm->card->snd_card; 882 const char *prefix; 883 size_t prefix_len; 884 int shared; 885 struct snd_kcontrol *kcontrol; 886 bool wname_in_long_name, kcname_in_long_name; 887 char *long_name = NULL; 888 const char *name; 889 int ret = 0; 890 891 prefix = soc_dapm_prefix(dapm); 892 if (prefix) 893 prefix_len = strlen(prefix) + 1; 894 else 895 prefix_len = 0; 896 897 shared = dapm_is_shared_kcontrol(dapm, w, &w->kcontrol_news[kci], 898 &kcontrol); 899 900 if (!kcontrol) { 901 if (shared) { 902 wname_in_long_name = false; 903 kcname_in_long_name = true; 904 } else { 905 switch (w->id) { 906 case snd_soc_dapm_switch: 907 case snd_soc_dapm_mixer: 908 case snd_soc_dapm_pga: 909 case snd_soc_dapm_effect: 910 case snd_soc_dapm_out_drv: 911 wname_in_long_name = true; 912 kcname_in_long_name = true; 913 break; 914 case snd_soc_dapm_mixer_named_ctl: 915 wname_in_long_name = false; 916 kcname_in_long_name = true; 917 break; 918 case snd_soc_dapm_demux: 919 case snd_soc_dapm_mux: 920 wname_in_long_name = true; 921 kcname_in_long_name = false; 922 break; 923 default: 924 return -EINVAL; 925 } 926 } 927 928 if (wname_in_long_name && kcname_in_long_name) { 929 /* 930 * The control will get a prefix from the control 931 * creation process but we're also using the same 932 * prefix for widgets so cut the prefix off the 933 * front of the widget name. 934 */ 935 long_name = kasprintf(GFP_KERNEL, "%s %s", 936 w->name + prefix_len, 937 w->kcontrol_news[kci].name); 938 if (long_name == NULL) 939 return -ENOMEM; 940 941 name = long_name; 942 } else if (wname_in_long_name) { 943 long_name = NULL; 944 name = w->name + prefix_len; 945 } else { 946 long_name = NULL; 947 name = w->kcontrol_news[kci].name; 948 } 949 950 kcontrol = snd_soc_cnew(&w->kcontrol_news[kci], NULL, name, 951 prefix); 952 if (!kcontrol) { 953 ret = -ENOMEM; 954 goto exit_free; 955 } 956 957 kcontrol->private_free = dapm_kcontrol_free; 958 959 ret = dapm_kcontrol_data_alloc(w, kcontrol, name); 960 if (ret) { 961 snd_ctl_free_one(kcontrol); 962 goto exit_free; 963 } 964 965 ret = snd_ctl_add(card, kcontrol); 966 if (ret < 0) { 967 dev_err(dapm->dev, 968 "ASoC: failed to add widget %s dapm kcontrol %s: %d\n", 969 w->name, name, ret); 970 goto exit_free; 971 } 972 } 973 974 ret = dapm_kcontrol_add_widget(kcontrol, w); 975 if (ret == 0) 976 w->kcontrols[kci] = kcontrol; 977 978exit_free: 979 kfree(long_name); 980 981 return ret; 982} 983 984/* create new dapm mixer control */ 985static int dapm_new_mixer(struct snd_soc_dapm_widget *w) 986{ 987 int i, ret; 988 struct snd_soc_dapm_path *path; 989 struct dapm_kcontrol_data *data; 990 991 /* add kcontrol */ 992 for (i = 0; i < w->num_kcontrols; i++) { 993 /* match name */ 994 snd_soc_dapm_widget_for_each_source_path(w, path) { 995 /* mixer/mux paths name must match control name */ 996 if (path->name != (char *)w->kcontrol_news[i].name) 997 continue; 998 999 if (!w->kcontrols[i]) { 1000 ret = dapm_create_or_share_kcontrol(w, i); 1001 if (ret < 0) 1002 return ret; 1003 } 1004 1005 dapm_kcontrol_add_path(w->kcontrols[i], path); 1006 1007 data = snd_kcontrol_chip(w->kcontrols[i]); 1008 if (data->widget) 1009 snd_soc_dapm_add_path(data->widget->dapm, 1010 data->widget, 1011 path->source, 1012 NULL, NULL); 1013 } 1014 } 1015 1016 return 0; 1017} 1018 1019/* create new dapm mux control */ 1020static int dapm_new_mux(struct snd_soc_dapm_widget *w) 1021{ 1022 struct snd_soc_dapm_context *dapm = w->dapm; 1023 enum snd_soc_dapm_direction dir; 1024 struct snd_soc_dapm_path *path; 1025 const char *type; 1026 int ret; 1027 1028 switch (w->id) { 1029 case snd_soc_dapm_mux: 1030 dir = SND_SOC_DAPM_DIR_OUT; 1031 type = "mux"; 1032 break; 1033 case snd_soc_dapm_demux: 1034 dir = SND_SOC_DAPM_DIR_IN; 1035 type = "demux"; 1036 break; 1037 default: 1038 return -EINVAL; 1039 } 1040 1041 if (w->num_kcontrols != 1) { 1042 dev_err(dapm->dev, 1043 "ASoC: %s %s has incorrect number of controls\n", type, 1044 w->name); 1045 return -EINVAL; 1046 } 1047 1048 if (list_empty(&w->edges[dir])) { 1049 dev_err(dapm->dev, "ASoC: %s %s has no paths\n", type, w->name); 1050 return -EINVAL; 1051 } 1052 1053 ret = dapm_create_or_share_kcontrol(w, 0); 1054 if (ret < 0) 1055 return ret; 1056 1057 snd_soc_dapm_widget_for_each_path(w, dir, path) { 1058 if (path->name) 1059 dapm_kcontrol_add_path(w->kcontrols[0], path); 1060 } 1061 1062 return 0; 1063} 1064 1065/* create new dapm volume control */ 1066static int dapm_new_pga(struct snd_soc_dapm_widget *w) 1067{ 1068 int i, ret; 1069 1070 for (i = 0; i < w->num_kcontrols; i++) { 1071 ret = dapm_create_or_share_kcontrol(w, i); 1072 if (ret < 0) 1073 return ret; 1074 } 1075 1076 return 0; 1077} 1078 1079/* create new dapm dai link control */ 1080static int dapm_new_dai_link(struct snd_soc_dapm_widget *w) 1081{ 1082 int i, ret; 1083 struct snd_kcontrol *kcontrol; 1084 struct snd_soc_dapm_context *dapm = w->dapm; 1085 struct snd_card *card = dapm->card->snd_card; 1086 struct snd_soc_pcm_runtime *rtd = w->priv; 1087 1088 /* create control for links with > 1 config */ 1089 if (rtd->dai_link->num_params <= 1) 1090 return 0; 1091 1092 /* add kcontrol */ 1093 for (i = 0; i < w->num_kcontrols; i++) { 1094 kcontrol = snd_soc_cnew(&w->kcontrol_news[i], w, 1095 w->name, NULL); 1096 ret = snd_ctl_add(card, kcontrol); 1097 if (ret < 0) { 1098 dev_err(dapm->dev, 1099 "ASoC: failed to add widget %s dapm kcontrol %s: %d\n", 1100 w->name, w->kcontrol_news[i].name, ret); 1101 return ret; 1102 } 1103 kcontrol->private_data = w; 1104 w->kcontrols[i] = kcontrol; 1105 } 1106 1107 return 0; 1108} 1109 1110/* We implement power down on suspend by checking the power state of 1111 * the ALSA card - when we are suspending the ALSA state for the card 1112 * is set to D3. 1113 */ 1114static int snd_soc_dapm_suspend_check(struct snd_soc_dapm_widget *widget) 1115{ 1116 int level = snd_power_get_state(widget->dapm->card->snd_card); 1117 1118 switch (level) { 1119 case SNDRV_CTL_POWER_D3hot: 1120 case SNDRV_CTL_POWER_D3cold: 1121 if (widget->ignore_suspend) 1122 dev_dbg(widget->dapm->dev, "ASoC: %s ignoring suspend\n", 1123 widget->name); 1124 return widget->ignore_suspend; 1125 default: 1126 return 1; 1127 } 1128} 1129 1130static void dapm_widget_list_free(struct snd_soc_dapm_widget_list **list) 1131{ 1132 kfree(*list); 1133} 1134 1135static int dapm_widget_list_create(struct snd_soc_dapm_widget_list **list, 1136 struct list_head *widgets) 1137{ 1138 struct snd_soc_dapm_widget *w; 1139 struct list_head *it; 1140 unsigned int size = 0; 1141 unsigned int i = 0; 1142 1143 list_for_each(it, widgets) 1144 size++; 1145 1146 *list = kzalloc(struct_size(*list, widgets, size), GFP_KERNEL); 1147 if (*list == NULL) 1148 return -ENOMEM; 1149 1150 list_for_each_entry(w, widgets, work_list) 1151 (*list)->widgets[i++] = w; 1152 1153 (*list)->num_widgets = i; 1154 1155 return 0; 1156} 1157 1158/* 1159 * Recursively reset the cached number of inputs or outputs for the specified 1160 * widget and all widgets that can be reached via incoming or outcoming paths 1161 * from the widget. 1162 */ 1163static void invalidate_paths_ep(struct snd_soc_dapm_widget *widget, 1164 enum snd_soc_dapm_direction dir) 1165{ 1166 enum snd_soc_dapm_direction rdir = SND_SOC_DAPM_DIR_REVERSE(dir); 1167 struct snd_soc_dapm_path *path; 1168 1169 widget->endpoints[dir] = -1; 1170 1171 snd_soc_dapm_widget_for_each_path(widget, rdir, path) { 1172 if (path->weak || path->is_supply) 1173 continue; 1174 1175 if (path->walking) 1176 return; 1177 1178 if (path->connect) { 1179 path->walking = 1; 1180 invalidate_paths_ep(path->node[dir], dir); 1181 path->walking = 0; 1182 } 1183 } 1184} 1185 1186/* 1187 * Common implementation for is_connected_output_ep() and 1188 * is_connected_input_ep(). The function is inlined since the combined size of 1189 * the two specialized functions is only marginally larger then the size of the 1190 * generic function and at the same time the fast path of the specialized 1191 * functions is significantly smaller than the generic function. 1192 */ 1193static __always_inline int is_connected_ep(struct snd_soc_dapm_widget *widget, 1194 struct list_head *list, enum snd_soc_dapm_direction dir, 1195 int (*fn)(struct snd_soc_dapm_widget *, struct list_head *, 1196 bool (*custom_stop_condition)(struct snd_soc_dapm_widget *, 1197 enum snd_soc_dapm_direction)), 1198 bool (*custom_stop_condition)(struct snd_soc_dapm_widget *, 1199 enum snd_soc_dapm_direction)) 1200{ 1201 enum snd_soc_dapm_direction rdir = SND_SOC_DAPM_DIR_REVERSE(dir); 1202 struct snd_soc_dapm_path *path; 1203 int con = 0; 1204 1205 if (widget->endpoints[dir] >= 0) 1206 return widget->endpoints[dir]; 1207 1208 DAPM_UPDATE_STAT(widget, path_checks); 1209 1210 /* do we need to add this widget to the list ? */ 1211 if (list) 1212 list_add_tail(&widget->work_list, list); 1213 1214 if (custom_stop_condition && custom_stop_condition(widget, dir)) { 1215 list = NULL; 1216 custom_stop_condition = NULL; 1217 } 1218 1219 if ((widget->is_ep & SND_SOC_DAPM_DIR_TO_EP(dir)) && widget->connected) { 1220 widget->endpoints[dir] = snd_soc_dapm_suspend_check(widget); 1221 return widget->endpoints[dir]; 1222 } 1223 1224 snd_soc_dapm_widget_for_each_path(widget, rdir, path) { 1225 DAPM_UPDATE_STAT(widget, neighbour_checks); 1226 1227 if (path->weak || path->is_supply) 1228 continue; 1229 1230 if (path->walking) 1231 return 1; 1232 1233 trace_snd_soc_dapm_path(widget, dir, path); 1234 1235 if (path->connect) { 1236 path->walking = 1; 1237 con += fn(path->node[dir], list, custom_stop_condition); 1238 path->walking = 0; 1239 } 1240 } 1241 1242 widget->endpoints[dir] = con; 1243 1244 return con; 1245} 1246 1247/* 1248 * Recursively check for a completed path to an active or physically connected 1249 * output widget. Returns number of complete paths. 1250 * 1251 * Optionally, can be supplied with a function acting as a stopping condition. 1252 * This function takes the dapm widget currently being examined and the walk 1253 * direction as an arguments, it should return true if widgets from that point 1254 * in the graph onwards should not be added to the widget list. 1255 */ 1256static int is_connected_output_ep(struct snd_soc_dapm_widget *widget, 1257 struct list_head *list, 1258 bool (*custom_stop_condition)(struct snd_soc_dapm_widget *i, 1259 enum snd_soc_dapm_direction)) 1260{ 1261 return is_connected_ep(widget, list, SND_SOC_DAPM_DIR_OUT, 1262 is_connected_output_ep, custom_stop_condition); 1263} 1264 1265/* 1266 * Recursively check for a completed path to an active or physically connected 1267 * input widget. Returns number of complete paths. 1268 * 1269 * Optionally, can be supplied with a function acting as a stopping condition. 1270 * This function takes the dapm widget currently being examined and the walk 1271 * direction as an arguments, it should return true if the walk should be 1272 * stopped and false otherwise. 1273 */ 1274static int is_connected_input_ep(struct snd_soc_dapm_widget *widget, 1275 struct list_head *list, 1276 bool (*custom_stop_condition)(struct snd_soc_dapm_widget *i, 1277 enum snd_soc_dapm_direction)) 1278{ 1279 return is_connected_ep(widget, list, SND_SOC_DAPM_DIR_IN, 1280 is_connected_input_ep, custom_stop_condition); 1281} 1282 1283/** 1284 * snd_soc_dapm_dai_get_connected_widgets - query audio path and it's widgets. 1285 * @dai: the soc DAI. 1286 * @stream: stream direction. 1287 * @list: list of active widgets for this stream. 1288 * @custom_stop_condition: (optional) a function meant to stop the widget graph 1289 * walk based on custom logic. 1290 * 1291 * Queries DAPM graph as to whether a valid audio stream path exists for 1292 * the initial stream specified by name. This takes into account 1293 * current mixer and mux kcontrol settings. Creates list of valid widgets. 1294 * 1295 * Optionally, can be supplied with a function acting as a stopping condition. 1296 * This function takes the dapm widget currently being examined and the walk 1297 * direction as an arguments, it should return true if the walk should be 1298 * stopped and false otherwise. 1299 * 1300 * Returns the number of valid paths or negative error. 1301 */ 1302int snd_soc_dapm_dai_get_connected_widgets(struct snd_soc_dai *dai, int stream, 1303 struct snd_soc_dapm_widget_list **list, 1304 bool (*custom_stop_condition)(struct snd_soc_dapm_widget *, 1305 enum snd_soc_dapm_direction)) 1306{ 1307 struct snd_soc_card *card = dai->component->card; 1308 struct snd_soc_dapm_widget *w; 1309 LIST_HEAD(widgets); 1310 int paths; 1311 int ret; 1312 1313 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 1314 1315 if (stream == SNDRV_PCM_STREAM_PLAYBACK) { 1316 w = dai->playback_widget; 1317 invalidate_paths_ep(w, SND_SOC_DAPM_DIR_OUT); 1318 paths = is_connected_output_ep(w, &widgets, 1319 custom_stop_condition); 1320 } else { 1321 w = dai->capture_widget; 1322 invalidate_paths_ep(w, SND_SOC_DAPM_DIR_IN); 1323 paths = is_connected_input_ep(w, &widgets, 1324 custom_stop_condition); 1325 } 1326 1327 /* Drop starting point */ 1328 list_del(widgets.next); 1329 1330 ret = dapm_widget_list_create(list, &widgets); 1331 if (ret) 1332 paths = ret; 1333 1334 trace_snd_soc_dapm_connected(paths, stream); 1335 mutex_unlock(&card->dapm_mutex); 1336 1337 return paths; 1338} 1339 1340void snd_soc_dapm_dai_free_widgets(struct snd_soc_dapm_widget_list **list) 1341{ 1342 dapm_widget_list_free(list); 1343} 1344 1345/* 1346 * Handler for regulator supply widget. 1347 */ 1348int dapm_regulator_event(struct snd_soc_dapm_widget *w, 1349 struct snd_kcontrol *kcontrol, int event) 1350{ 1351 int ret; 1352 1353 soc_dapm_async_complete(w->dapm); 1354 1355 if (SND_SOC_DAPM_EVENT_ON(event)) { 1356 if (w->on_val & SND_SOC_DAPM_REGULATOR_BYPASS) { 1357 ret = regulator_allow_bypass(w->regulator, false); 1358 if (ret != 0) 1359 dev_warn(w->dapm->dev, 1360 "ASoC: Failed to unbypass %s: %d\n", 1361 w->name, ret); 1362 } 1363 1364 return regulator_enable(w->regulator); 1365 } else { 1366 if (w->on_val & SND_SOC_DAPM_REGULATOR_BYPASS) { 1367 ret = regulator_allow_bypass(w->regulator, true); 1368 if (ret != 0) 1369 dev_warn(w->dapm->dev, 1370 "ASoC: Failed to bypass %s: %d\n", 1371 w->name, ret); 1372 } 1373 1374 return regulator_disable_deferred(w->regulator, w->shift); 1375 } 1376} 1377EXPORT_SYMBOL_GPL(dapm_regulator_event); 1378 1379/* 1380 * Handler for pinctrl widget. 1381 */ 1382int dapm_pinctrl_event(struct snd_soc_dapm_widget *w, 1383 struct snd_kcontrol *kcontrol, int event) 1384{ 1385 struct snd_soc_dapm_pinctrl_priv *priv = w->priv; 1386 struct pinctrl *p = w->pinctrl; 1387 struct pinctrl_state *s; 1388 1389 if (!p || !priv) 1390 return -EIO; 1391 1392 if (SND_SOC_DAPM_EVENT_ON(event)) 1393 s = pinctrl_lookup_state(p, priv->active_state); 1394 else 1395 s = pinctrl_lookup_state(p, priv->sleep_state); 1396 1397 if (IS_ERR(s)) 1398 return PTR_ERR(s); 1399 1400 return pinctrl_select_state(p, s); 1401} 1402EXPORT_SYMBOL_GPL(dapm_pinctrl_event); 1403 1404/* 1405 * Handler for clock supply widget. 1406 */ 1407int dapm_clock_event(struct snd_soc_dapm_widget *w, 1408 struct snd_kcontrol *kcontrol, int event) 1409{ 1410 if (!w->clk) 1411 return -EIO; 1412 1413 soc_dapm_async_complete(w->dapm); 1414 1415 if (SND_SOC_DAPM_EVENT_ON(event)) { 1416 return clk_prepare_enable(w->clk); 1417 } else { 1418 clk_disable_unprepare(w->clk); 1419 return 0; 1420 } 1421 1422 return 0; 1423} 1424EXPORT_SYMBOL_GPL(dapm_clock_event); 1425 1426static int dapm_widget_power_check(struct snd_soc_dapm_widget *w) 1427{ 1428 if (w->power_checked) 1429 return w->new_power; 1430 1431 if (w->force) 1432 w->new_power = 1; 1433 else 1434 w->new_power = w->power_check(w); 1435 1436 w->power_checked = true; 1437 1438 return w->new_power; 1439} 1440 1441/* Generic check to see if a widget should be powered. */ 1442static int dapm_generic_check_power(struct snd_soc_dapm_widget *w) 1443{ 1444 int in, out; 1445 1446 DAPM_UPDATE_STAT(w, power_checks); 1447 1448 in = is_connected_input_ep(w, NULL, NULL); 1449 out = is_connected_output_ep(w, NULL, NULL); 1450 return out != 0 && in != 0; 1451} 1452 1453/* Check to see if a power supply is needed */ 1454static int dapm_supply_check_power(struct snd_soc_dapm_widget *w) 1455{ 1456 struct snd_soc_dapm_path *path; 1457 1458 DAPM_UPDATE_STAT(w, power_checks); 1459 1460 /* Check if one of our outputs is connected */ 1461 snd_soc_dapm_widget_for_each_sink_path(w, path) { 1462 DAPM_UPDATE_STAT(w, neighbour_checks); 1463 1464 if (path->weak) 1465 continue; 1466 1467 if (path->connected && 1468 !path->connected(path->source, path->sink)) 1469 continue; 1470 1471 if (dapm_widget_power_check(path->sink)) 1472 return 1; 1473 } 1474 1475 return 0; 1476} 1477 1478static int dapm_always_on_check_power(struct snd_soc_dapm_widget *w) 1479{ 1480 return w->connected; 1481} 1482 1483static int dapm_seq_compare(struct snd_soc_dapm_widget *a, 1484 struct snd_soc_dapm_widget *b, 1485 bool power_up) 1486{ 1487 int *sort; 1488 1489 BUILD_BUG_ON(ARRAY_SIZE(dapm_up_seq) != SND_SOC_DAPM_TYPE_COUNT); 1490 BUILD_BUG_ON(ARRAY_SIZE(dapm_down_seq) != SND_SOC_DAPM_TYPE_COUNT); 1491 1492 if (power_up) 1493 sort = dapm_up_seq; 1494 else 1495 sort = dapm_down_seq; 1496 1497 WARN_ONCE(sort[a->id] == 0, "offset a->id %d not initialized\n", a->id); 1498 WARN_ONCE(sort[b->id] == 0, "offset b->id %d not initialized\n", b->id); 1499 1500 if (sort[a->id] != sort[b->id]) 1501 return sort[a->id] - sort[b->id]; 1502 if (a->subseq != b->subseq) { 1503 if (power_up) 1504 return a->subseq - b->subseq; 1505 else 1506 return b->subseq - a->subseq; 1507 } 1508 if (a->reg != b->reg) 1509 return a->reg - b->reg; 1510 if (a->dapm != b->dapm) 1511 return (unsigned long)a->dapm - (unsigned long)b->dapm; 1512 1513 return 0; 1514} 1515 1516/* Insert a widget in order into a DAPM power sequence. */ 1517static void dapm_seq_insert(struct snd_soc_dapm_widget *new_widget, 1518 struct list_head *list, 1519 bool power_up) 1520{ 1521 struct snd_soc_dapm_widget *w; 1522 1523 list_for_each_entry(w, list, power_list) 1524 if (dapm_seq_compare(new_widget, w, power_up) < 0) { 1525 list_add_tail(&new_widget->power_list, &w->power_list); 1526 return; 1527 } 1528 1529 list_add_tail(&new_widget->power_list, list); 1530} 1531 1532static void dapm_seq_check_event(struct snd_soc_card *card, 1533 struct snd_soc_dapm_widget *w, int event) 1534{ 1535 const char *ev_name; 1536 int power, ret; 1537 1538 switch (event) { 1539 case SND_SOC_DAPM_PRE_PMU: 1540 ev_name = "PRE_PMU"; 1541 power = 1; 1542 break; 1543 case SND_SOC_DAPM_POST_PMU: 1544 ev_name = "POST_PMU"; 1545 power = 1; 1546 break; 1547 case SND_SOC_DAPM_PRE_PMD: 1548 ev_name = "PRE_PMD"; 1549 power = 0; 1550 break; 1551 case SND_SOC_DAPM_POST_PMD: 1552 ev_name = "POST_PMD"; 1553 power = 0; 1554 break; 1555 case SND_SOC_DAPM_WILL_PMU: 1556 ev_name = "WILL_PMU"; 1557 power = 1; 1558 break; 1559 case SND_SOC_DAPM_WILL_PMD: 1560 ev_name = "WILL_PMD"; 1561 power = 0; 1562 break; 1563 default: 1564 WARN(1, "Unknown event %d\n", event); 1565 return; 1566 } 1567 1568 if (w->new_power != power) 1569 return; 1570 1571 if (w->event && (w->event_flags & event)) { 1572 pop_dbg(w->dapm->dev, card->pop_time, "pop test : %s %s\n", 1573 w->name, ev_name); 1574 soc_dapm_async_complete(w->dapm); 1575 trace_snd_soc_dapm_widget_event_start(w, event); 1576 ret = w->event(w, NULL, event); 1577 trace_snd_soc_dapm_widget_event_done(w, event); 1578 if (ret < 0) 1579 dev_err(w->dapm->dev, "ASoC: %s: %s event failed: %d\n", 1580 ev_name, w->name, ret); 1581 } 1582} 1583 1584/* Apply the coalesced changes from a DAPM sequence */ 1585static void dapm_seq_run_coalesced(struct snd_soc_card *card, 1586 struct list_head *pending) 1587{ 1588 struct snd_soc_dapm_context *dapm; 1589 struct snd_soc_dapm_widget *w; 1590 int reg; 1591 unsigned int value = 0; 1592 unsigned int mask = 0; 1593 1594 w = list_first_entry(pending, struct snd_soc_dapm_widget, power_list); 1595 reg = w->reg; 1596 dapm = w->dapm; 1597 1598 list_for_each_entry(w, pending, power_list) { 1599 WARN_ON(reg != w->reg || dapm != w->dapm); 1600 w->power = w->new_power; 1601 1602 mask |= w->mask << w->shift; 1603 if (w->power) 1604 value |= w->on_val << w->shift; 1605 else 1606 value |= w->off_val << w->shift; 1607 1608 pop_dbg(dapm->dev, card->pop_time, 1609 "pop test : Queue %s: reg=0x%x, 0x%x/0x%x\n", 1610 w->name, reg, value, mask); 1611 1612 /* Check for events */ 1613 dapm_seq_check_event(card, w, SND_SOC_DAPM_PRE_PMU); 1614 dapm_seq_check_event(card, w, SND_SOC_DAPM_PRE_PMD); 1615 } 1616 1617 if (reg >= 0) { 1618 /* Any widget will do, they should all be updating the 1619 * same register. 1620 */ 1621 1622 pop_dbg(dapm->dev, card->pop_time, 1623 "pop test : Applying 0x%x/0x%x to %x in %dms\n", 1624 value, mask, reg, card->pop_time); 1625 pop_wait(card->pop_time); 1626 soc_dapm_update_bits(dapm, reg, mask, value); 1627 } 1628 1629 list_for_each_entry(w, pending, power_list) { 1630 dapm_seq_check_event(card, w, SND_SOC_DAPM_POST_PMU); 1631 dapm_seq_check_event(card, w, SND_SOC_DAPM_POST_PMD); 1632 } 1633} 1634 1635/* Apply a DAPM power sequence. 1636 * 1637 * We walk over a pre-sorted list of widgets to apply power to. In 1638 * order to minimise the number of writes to the device required 1639 * multiple widgets will be updated in a single write where possible. 1640 * Currently anything that requires more than a single write is not 1641 * handled. 1642 */ 1643static void dapm_seq_run(struct snd_soc_card *card, 1644 struct list_head *list, int event, bool power_up) 1645{ 1646 struct snd_soc_dapm_widget *w, *n; 1647 struct snd_soc_dapm_context *d; 1648 LIST_HEAD(pending); 1649 int cur_sort = -1; 1650 int cur_subseq = -1; 1651 int cur_reg = SND_SOC_NOPM; 1652 struct snd_soc_dapm_context *cur_dapm = NULL; 1653 int ret, i; 1654 int *sort; 1655 1656 if (power_up) 1657 sort = dapm_up_seq; 1658 else 1659 sort = dapm_down_seq; 1660 1661 list_for_each_entry_safe(w, n, list, power_list) { 1662 ret = 0; 1663 1664 /* Do we need to apply any queued changes? */ 1665 if (sort[w->id] != cur_sort || w->reg != cur_reg || 1666 w->dapm != cur_dapm || w->subseq != cur_subseq) { 1667 if (!list_empty(&pending)) 1668 dapm_seq_run_coalesced(card, &pending); 1669 1670 if (cur_dapm && cur_dapm->component) { 1671 for (i = 0; i < ARRAY_SIZE(dapm_up_seq); i++) 1672 if (sort[i] == cur_sort) 1673 snd_soc_component_seq_notifier( 1674 cur_dapm->component, 1675 i, cur_subseq); 1676 } 1677 1678 if (cur_dapm && w->dapm != cur_dapm) 1679 soc_dapm_async_complete(cur_dapm); 1680 1681 INIT_LIST_HEAD(&pending); 1682 cur_sort = -1; 1683 cur_subseq = INT_MIN; 1684 cur_reg = SND_SOC_NOPM; 1685 cur_dapm = NULL; 1686 } 1687 1688 switch (w->id) { 1689 case snd_soc_dapm_pre: 1690 if (!w->event) 1691 continue; 1692 1693 if (event == SND_SOC_DAPM_STREAM_START) 1694 ret = w->event(w, 1695 NULL, SND_SOC_DAPM_PRE_PMU); 1696 else if (event == SND_SOC_DAPM_STREAM_STOP) 1697 ret = w->event(w, 1698 NULL, SND_SOC_DAPM_PRE_PMD); 1699 break; 1700 1701 case snd_soc_dapm_post: 1702 if (!w->event) 1703 continue; 1704 1705 if (event == SND_SOC_DAPM_STREAM_START) 1706 ret = w->event(w, 1707 NULL, SND_SOC_DAPM_POST_PMU); 1708 else if (event == SND_SOC_DAPM_STREAM_STOP) 1709 ret = w->event(w, 1710 NULL, SND_SOC_DAPM_POST_PMD); 1711 break; 1712 1713 default: 1714 /* Queue it up for application */ 1715 cur_sort = sort[w->id]; 1716 cur_subseq = w->subseq; 1717 cur_reg = w->reg; 1718 cur_dapm = w->dapm; 1719 list_move(&w->power_list, &pending); 1720 break; 1721 } 1722 1723 if (ret < 0) 1724 dev_err(w->dapm->dev, 1725 "ASoC: Failed to apply widget power: %d\n", ret); 1726 } 1727 1728 if (!list_empty(&pending)) 1729 dapm_seq_run_coalesced(card, &pending); 1730 1731 if (cur_dapm && cur_dapm->component) { 1732 for (i = 0; i < ARRAY_SIZE(dapm_up_seq); i++) 1733 if (sort[i] == cur_sort) 1734 snd_soc_component_seq_notifier( 1735 cur_dapm->component, 1736 i, cur_subseq); 1737 } 1738 1739 for_each_card_dapms(card, d) 1740 soc_dapm_async_complete(d); 1741} 1742 1743static void dapm_widget_update(struct snd_soc_card *card) 1744{ 1745 struct snd_soc_dapm_update *update = card->update; 1746 struct snd_soc_dapm_widget_list *wlist; 1747 struct snd_soc_dapm_widget *w = NULL; 1748 unsigned int wi; 1749 int ret; 1750 1751 if (!update || !dapm_kcontrol_is_powered(update->kcontrol)) 1752 return; 1753 1754 wlist = dapm_kcontrol_get_wlist(update->kcontrol); 1755 1756 for_each_dapm_widgets(wlist, wi, w) { 1757 if (w->event && (w->event_flags & SND_SOC_DAPM_PRE_REG)) { 1758 ret = w->event(w, update->kcontrol, SND_SOC_DAPM_PRE_REG); 1759 if (ret != 0) 1760 dev_err(w->dapm->dev, "ASoC: %s DAPM pre-event failed: %d\n", 1761 w->name, ret); 1762 } 1763 } 1764 1765 if (!w) 1766 return; 1767 1768 ret = soc_dapm_update_bits(w->dapm, update->reg, update->mask, 1769 update->val); 1770 if (ret < 0) 1771 dev_err(w->dapm->dev, "ASoC: %s DAPM update failed: %d\n", 1772 w->name, ret); 1773 1774 if (update->has_second_set) { 1775 ret = soc_dapm_update_bits(w->dapm, update->reg2, 1776 update->mask2, update->val2); 1777 if (ret < 0) 1778 dev_err(w->dapm->dev, 1779 "ASoC: %s DAPM update failed: %d\n", 1780 w->name, ret); 1781 } 1782 1783 for_each_dapm_widgets(wlist, wi, w) { 1784 if (w->event && (w->event_flags & SND_SOC_DAPM_POST_REG)) { 1785 ret = w->event(w, update->kcontrol, SND_SOC_DAPM_POST_REG); 1786 if (ret != 0) 1787 dev_err(w->dapm->dev, "ASoC: %s DAPM post-event failed: %d\n", 1788 w->name, ret); 1789 } 1790 } 1791} 1792 1793/* Async callback run prior to DAPM sequences - brings to _PREPARE if 1794 * they're changing state. 1795 */ 1796static void dapm_pre_sequence_async(void *data, async_cookie_t cookie) 1797{ 1798 struct snd_soc_dapm_context *d = data; 1799 int ret; 1800 1801 /* If we're off and we're not supposed to go into STANDBY */ 1802 if (d->bias_level == SND_SOC_BIAS_OFF && 1803 d->target_bias_level != SND_SOC_BIAS_OFF) { 1804 if (d->dev && cookie) 1805 pm_runtime_get_sync(d->dev); 1806 1807 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_STANDBY); 1808 if (ret != 0) 1809 dev_err(d->dev, 1810 "ASoC: Failed to turn on bias: %d\n", ret); 1811 } 1812 1813 /* Prepare for a transition to ON or away from ON */ 1814 if ((d->target_bias_level == SND_SOC_BIAS_ON && 1815 d->bias_level != SND_SOC_BIAS_ON) || 1816 (d->target_bias_level != SND_SOC_BIAS_ON && 1817 d->bias_level == SND_SOC_BIAS_ON)) { 1818 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_PREPARE); 1819 if (ret != 0) 1820 dev_err(d->dev, 1821 "ASoC: Failed to prepare bias: %d\n", ret); 1822 } 1823} 1824 1825/* Async callback run prior to DAPM sequences - brings to their final 1826 * state. 1827 */ 1828static void dapm_post_sequence_async(void *data, async_cookie_t cookie) 1829{ 1830 struct snd_soc_dapm_context *d = data; 1831 int ret; 1832 1833 /* If we just powered the last thing off drop to standby bias */ 1834 if (d->bias_level == SND_SOC_BIAS_PREPARE && 1835 (d->target_bias_level == SND_SOC_BIAS_STANDBY || 1836 d->target_bias_level == SND_SOC_BIAS_OFF)) { 1837 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_STANDBY); 1838 if (ret != 0) 1839 dev_err(d->dev, "ASoC: Failed to apply standby bias: %d\n", 1840 ret); 1841 } 1842 1843 /* If we're in standby and can support bias off then do that */ 1844 if (d->bias_level == SND_SOC_BIAS_STANDBY && 1845 d->target_bias_level == SND_SOC_BIAS_OFF) { 1846 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_OFF); 1847 if (ret != 0) 1848 dev_err(d->dev, "ASoC: Failed to turn off bias: %d\n", 1849 ret); 1850 1851 if (d->dev && cookie) 1852 pm_runtime_put(d->dev); 1853 } 1854 1855 /* If we just powered up then move to active bias */ 1856 if (d->bias_level == SND_SOC_BIAS_PREPARE && 1857 d->target_bias_level == SND_SOC_BIAS_ON) { 1858 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_ON); 1859 if (ret != 0) 1860 dev_err(d->dev, "ASoC: Failed to apply active bias: %d\n", 1861 ret); 1862 } 1863} 1864 1865static void dapm_widget_set_peer_power(struct snd_soc_dapm_widget *peer, 1866 bool power, bool connect) 1867{ 1868 /* If a connection is being made or broken then that update 1869 * will have marked the peer dirty, otherwise the widgets are 1870 * not connected and this update has no impact. */ 1871 if (!connect) 1872 return; 1873 1874 /* If the peer is already in the state we're moving to then we 1875 * won't have an impact on it. */ 1876 if (power != peer->power) 1877 dapm_mark_dirty(peer, "peer state change"); 1878} 1879 1880static void dapm_widget_set_power(struct snd_soc_dapm_widget *w, bool power, 1881 struct list_head *up_list, 1882 struct list_head *down_list) 1883{ 1884 struct snd_soc_dapm_path *path; 1885 1886 if (w->power == power) 1887 return; 1888 1889 trace_snd_soc_dapm_widget_power(w, power); 1890 1891 /* If we changed our power state perhaps our neigbours changed 1892 * also. 1893 */ 1894 snd_soc_dapm_widget_for_each_source_path(w, path) 1895 dapm_widget_set_peer_power(path->source, power, path->connect); 1896 1897 /* Supplies can't affect their outputs, only their inputs */ 1898 if (!w->is_supply) { 1899 snd_soc_dapm_widget_for_each_sink_path(w, path) 1900 dapm_widget_set_peer_power(path->sink, power, 1901 path->connect); 1902 } 1903 1904 if (power) 1905 dapm_seq_insert(w, up_list, true); 1906 else 1907 dapm_seq_insert(w, down_list, false); 1908} 1909 1910static void dapm_power_one_widget(struct snd_soc_dapm_widget *w, 1911 struct list_head *up_list, 1912 struct list_head *down_list) 1913{ 1914 int power; 1915 1916 switch (w->id) { 1917 case snd_soc_dapm_pre: 1918 dapm_seq_insert(w, down_list, false); 1919 break; 1920 case snd_soc_dapm_post: 1921 dapm_seq_insert(w, up_list, true); 1922 break; 1923 1924 default: 1925 power = dapm_widget_power_check(w); 1926 1927 dapm_widget_set_power(w, power, up_list, down_list); 1928 break; 1929 } 1930} 1931 1932static bool dapm_idle_bias_off(struct snd_soc_dapm_context *dapm) 1933{ 1934 if (dapm->idle_bias_off) 1935 return true; 1936 1937 switch (snd_power_get_state(dapm->card->snd_card)) { 1938 case SNDRV_CTL_POWER_D3hot: 1939 case SNDRV_CTL_POWER_D3cold: 1940 return dapm->suspend_bias_off; 1941 default: 1942 break; 1943 } 1944 1945 return false; 1946} 1947 1948/* 1949 * Scan each dapm widget for complete audio path. 1950 * A complete path is a route that has valid endpoints i.e.:- 1951 * 1952 * o DAC to output pin. 1953 * o Input pin to ADC. 1954 * o Input pin to Output pin (bypass, sidetone) 1955 * o DAC to ADC (loopback). 1956 */ 1957static int dapm_power_widgets(struct snd_soc_card *card, int event) 1958{ 1959 struct snd_soc_dapm_widget *w; 1960 struct snd_soc_dapm_context *d; 1961 LIST_HEAD(up_list); 1962 LIST_HEAD(down_list); 1963 ASYNC_DOMAIN_EXCLUSIVE(async_domain); 1964 enum snd_soc_bias_level bias; 1965 int ret; 1966 1967 lockdep_assert_held(&card->dapm_mutex); 1968 1969 trace_snd_soc_dapm_start(card); 1970 1971 for_each_card_dapms(card, d) { 1972 if (dapm_idle_bias_off(d)) 1973 d->target_bias_level = SND_SOC_BIAS_OFF; 1974 else 1975 d->target_bias_level = SND_SOC_BIAS_STANDBY; 1976 } 1977 1978 dapm_reset(card); 1979 1980 /* Check which widgets we need to power and store them in 1981 * lists indicating if they should be powered up or down. We 1982 * only check widgets that have been flagged as dirty but note 1983 * that new widgets may be added to the dirty list while we 1984 * iterate. 1985 */ 1986 list_for_each_entry(w, &card->dapm_dirty, dirty) { 1987 dapm_power_one_widget(w, &up_list, &down_list); 1988 } 1989 1990 for_each_card_widgets(card, w) { 1991 switch (w->id) { 1992 case snd_soc_dapm_pre: 1993 case snd_soc_dapm_post: 1994 /* These widgets always need to be powered */ 1995 break; 1996 default: 1997 list_del_init(&w->dirty); 1998 break; 1999 } 2000 2001 if (w->new_power) { 2002 d = w->dapm; 2003 2004 /* Supplies and micbiases only bring the 2005 * context up to STANDBY as unless something 2006 * else is active and passing audio they 2007 * generally don't require full power. Signal 2008 * generators are virtual pins and have no 2009 * power impact themselves. 2010 */ 2011 switch (w->id) { 2012 case snd_soc_dapm_siggen: 2013 case snd_soc_dapm_vmid: 2014 break; 2015 case snd_soc_dapm_supply: 2016 case snd_soc_dapm_regulator_supply: 2017 case snd_soc_dapm_pinctrl: 2018 case snd_soc_dapm_clock_supply: 2019 case snd_soc_dapm_micbias: 2020 if (d->target_bias_level < SND_SOC_BIAS_STANDBY) 2021 d->target_bias_level = SND_SOC_BIAS_STANDBY; 2022 break; 2023 default: 2024 d->target_bias_level = SND_SOC_BIAS_ON; 2025 break; 2026 } 2027 } 2028 2029 } 2030 2031 /* Force all contexts in the card to the same bias state if 2032 * they're not ground referenced. 2033 */ 2034 bias = SND_SOC_BIAS_OFF; 2035 for_each_card_dapms(card, d) 2036 if (d->target_bias_level > bias) 2037 bias = d->target_bias_level; 2038 for_each_card_dapms(card, d) 2039 if (!dapm_idle_bias_off(d)) 2040 d->target_bias_level = bias; 2041 2042 trace_snd_soc_dapm_walk_done(card); 2043 2044 /* Run card bias changes at first */ 2045 dapm_pre_sequence_async(&card->dapm, 0); 2046 /* Run other bias changes in parallel */ 2047 for_each_card_dapms(card, d) { 2048 if (d != &card->dapm && d->bias_level != d->target_bias_level) 2049 async_schedule_domain(dapm_pre_sequence_async, d, 2050 &async_domain); 2051 } 2052 async_synchronize_full_domain(&async_domain); 2053 2054 list_for_each_entry(w, &down_list, power_list) { 2055 dapm_seq_check_event(card, w, SND_SOC_DAPM_WILL_PMD); 2056 } 2057 2058 list_for_each_entry(w, &up_list, power_list) { 2059 dapm_seq_check_event(card, w, SND_SOC_DAPM_WILL_PMU); 2060 } 2061 2062 /* Power down widgets first; try to avoid amplifying pops. */ 2063 dapm_seq_run(card, &down_list, event, false); 2064 2065 dapm_widget_update(card); 2066 2067 /* Now power up. */ 2068 dapm_seq_run(card, &up_list, event, true); 2069 2070 /* Run all the bias changes in parallel */ 2071 for_each_card_dapms(card, d) { 2072 if (d != &card->dapm && d->bias_level != d->target_bias_level) 2073 async_schedule_domain(dapm_post_sequence_async, d, 2074 &async_domain); 2075 } 2076 async_synchronize_full_domain(&async_domain); 2077 /* Run card bias changes at last */ 2078 dapm_post_sequence_async(&card->dapm, 0); 2079 2080 /* do we need to notify any clients that DAPM event is complete */ 2081 for_each_card_dapms(card, d) { 2082 if (!d->component) 2083 continue; 2084 2085 ret = snd_soc_component_stream_event(d->component, event); 2086 if (ret < 0) 2087 return ret; 2088 } 2089 2090 pop_dbg(card->dev, card->pop_time, 2091 "DAPM sequencing finished, waiting %dms\n", card->pop_time); 2092 pop_wait(card->pop_time); 2093 2094 trace_snd_soc_dapm_done(card); 2095 2096 return 0; 2097} 2098 2099#ifdef CONFIG_DEBUG_FS 2100static ssize_t dapm_widget_power_read_file(struct file *file, 2101 char __user *user_buf, 2102 size_t count, loff_t *ppos) 2103{ 2104 struct snd_soc_dapm_widget *w = file->private_data; 2105 struct snd_soc_card *card = w->dapm->card; 2106 enum snd_soc_dapm_direction dir, rdir; 2107 char *buf; 2108 int in, out; 2109 ssize_t ret; 2110 struct snd_soc_dapm_path *p = NULL; 2111 2112 buf = kmalloc(PAGE_SIZE, GFP_KERNEL); 2113 if (!buf) 2114 return -ENOMEM; 2115 2116 mutex_lock(&card->dapm_mutex); 2117 2118 /* Supply widgets are not handled by is_connected_{input,output}_ep() */ 2119 if (w->is_supply) { 2120 in = 0; 2121 out = 0; 2122 } else { 2123 in = is_connected_input_ep(w, NULL, NULL); 2124 out = is_connected_output_ep(w, NULL, NULL); 2125 } 2126 2127 ret = scnprintf(buf, PAGE_SIZE, "%s: %s%s in %d out %d", 2128 w->name, w->power ? "On" : "Off", 2129 w->force ? " (forced)" : "", in, out); 2130 2131 if (w->reg >= 0) 2132 ret += scnprintf(buf + ret, PAGE_SIZE - ret, 2133 " - R%d(0x%x) mask 0x%x", 2134 w->reg, w->reg, w->mask << w->shift); 2135 2136 ret += scnprintf(buf + ret, PAGE_SIZE - ret, "\n"); 2137 2138 if (w->sname) 2139 ret += scnprintf(buf + ret, PAGE_SIZE - ret, " stream %s %s\n", 2140 w->sname, 2141 w->active ? "active" : "inactive"); 2142 2143 snd_soc_dapm_for_each_direction(dir) { 2144 rdir = SND_SOC_DAPM_DIR_REVERSE(dir); 2145 snd_soc_dapm_widget_for_each_path(w, dir, p) { 2146 if (p->connected && !p->connected(p->source, p->sink)) 2147 continue; 2148 2149 if (!p->connect) 2150 continue; 2151 2152 ret += scnprintf(buf + ret, PAGE_SIZE - ret, 2153 " %s \"%s\" \"%s\"\n", 2154 (rdir == SND_SOC_DAPM_DIR_IN) ? "in" : "out", 2155 p->name ? p->name : "static", 2156 p->node[rdir]->name); 2157 } 2158 } 2159 2160 mutex_unlock(&card->dapm_mutex); 2161 2162 ret = simple_read_from_buffer(user_buf, count, ppos, buf, ret); 2163 2164 kfree(buf); 2165 return ret; 2166} 2167 2168static const struct file_operations dapm_widget_power_fops = { 2169 .open = simple_open, 2170 .read = dapm_widget_power_read_file, 2171 .llseek = default_llseek, 2172}; 2173 2174static ssize_t dapm_bias_read_file(struct file *file, char __user *user_buf, 2175 size_t count, loff_t *ppos) 2176{ 2177 struct snd_soc_dapm_context *dapm = file->private_data; 2178 char *level; 2179 2180 switch (dapm->bias_level) { 2181 case SND_SOC_BIAS_ON: 2182 level = "On\n"; 2183 break; 2184 case SND_SOC_BIAS_PREPARE: 2185 level = "Prepare\n"; 2186 break; 2187 case SND_SOC_BIAS_STANDBY: 2188 level = "Standby\n"; 2189 break; 2190 case SND_SOC_BIAS_OFF: 2191 level = "Off\n"; 2192 break; 2193 default: 2194 WARN(1, "Unknown bias_level %d\n", dapm->bias_level); 2195 level = "Unknown\n"; 2196 break; 2197 } 2198 2199 return simple_read_from_buffer(user_buf, count, ppos, level, 2200 strlen(level)); 2201} 2202 2203static const struct file_operations dapm_bias_fops = { 2204 .open = simple_open, 2205 .read = dapm_bias_read_file, 2206 .llseek = default_llseek, 2207}; 2208 2209void snd_soc_dapm_debugfs_init(struct snd_soc_dapm_context *dapm, 2210 struct dentry *parent) 2211{ 2212 if (!parent || IS_ERR(parent)) 2213 return; 2214 2215 dapm->debugfs_dapm = debugfs_create_dir("dapm", parent); 2216 2217 debugfs_create_file("bias_level", 0444, dapm->debugfs_dapm, dapm, 2218 &dapm_bias_fops); 2219} 2220 2221static void dapm_debugfs_add_widget(struct snd_soc_dapm_widget *w) 2222{ 2223 struct snd_soc_dapm_context *dapm = w->dapm; 2224 2225 if (!dapm->debugfs_dapm || !w->name) 2226 return; 2227 2228 debugfs_create_file(w->name, 0444, dapm->debugfs_dapm, w, 2229 &dapm_widget_power_fops); 2230} 2231 2232static void dapm_debugfs_cleanup(struct snd_soc_dapm_context *dapm) 2233{ 2234 debugfs_remove_recursive(dapm->debugfs_dapm); 2235 dapm->debugfs_dapm = NULL; 2236} 2237 2238#else 2239void snd_soc_dapm_debugfs_init(struct snd_soc_dapm_context *dapm, 2240 struct dentry *parent) 2241{ 2242} 2243 2244static inline void dapm_debugfs_add_widget(struct snd_soc_dapm_widget *w) 2245{ 2246} 2247 2248static inline void dapm_debugfs_cleanup(struct snd_soc_dapm_context *dapm) 2249{ 2250} 2251 2252#endif 2253 2254/* 2255 * soc_dapm_connect_path() - Connects or disconnects a path 2256 * @path: The path to update 2257 * @connect: The new connect state of the path. True if the path is connected, 2258 * false if it is disconnected. 2259 * @reason: The reason why the path changed (for debugging only) 2260 */ 2261static void soc_dapm_connect_path(struct snd_soc_dapm_path *path, 2262 bool connect, const char *reason) 2263{ 2264 if (path->connect == connect) 2265 return; 2266 2267 path->connect = connect; 2268 dapm_mark_dirty(path->source, reason); 2269 dapm_mark_dirty(path->sink, reason); 2270 dapm_path_invalidate(path); 2271} 2272 2273/* test and update the power status of a mux widget */ 2274static int soc_dapm_mux_update_power(struct snd_soc_card *card, 2275 struct snd_kcontrol *kcontrol, int mux, struct soc_enum *e) 2276{ 2277 struct snd_soc_dapm_path *path; 2278 int found = 0; 2279 bool connect; 2280 2281 lockdep_assert_held(&card->dapm_mutex); 2282 2283 /* find dapm widget path assoc with kcontrol */ 2284 dapm_kcontrol_for_each_path(path, kcontrol) { 2285 found = 1; 2286 /* we now need to match the string in the enum to the path */ 2287 if (e && !(strcmp(path->name, e->texts[mux]))) 2288 connect = true; 2289 else 2290 connect = false; 2291 2292 soc_dapm_connect_path(path, connect, "mux update"); 2293 } 2294 2295 if (found) 2296 dapm_power_widgets(card, SND_SOC_DAPM_STREAM_NOP); 2297 2298 return found; 2299} 2300 2301int snd_soc_dapm_mux_update_power(struct snd_soc_dapm_context *dapm, 2302 struct snd_kcontrol *kcontrol, int mux, struct soc_enum *e, 2303 struct snd_soc_dapm_update *update) 2304{ 2305 struct snd_soc_card *card = dapm->card; 2306 int ret; 2307 2308 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 2309 card->update = update; 2310 ret = soc_dapm_mux_update_power(card, kcontrol, mux, e); 2311 card->update = NULL; 2312 mutex_unlock(&card->dapm_mutex); 2313 if (ret > 0) 2314 snd_soc_dpcm_runtime_update(card); 2315 return ret; 2316} 2317EXPORT_SYMBOL_GPL(snd_soc_dapm_mux_update_power); 2318 2319/* test and update the power status of a mixer or switch widget */ 2320static int soc_dapm_mixer_update_power(struct snd_soc_card *card, 2321 struct snd_kcontrol *kcontrol, 2322 int connect, int rconnect) 2323{ 2324 struct snd_soc_dapm_path *path; 2325 int found = 0; 2326 2327 lockdep_assert_held(&card->dapm_mutex); 2328 2329 /* find dapm widget path assoc with kcontrol */ 2330 dapm_kcontrol_for_each_path(path, kcontrol) { 2331 /* 2332 * Ideally this function should support any number of 2333 * paths and channels. But since kcontrols only come 2334 * in mono and stereo variants, we are limited to 2 2335 * channels. 2336 * 2337 * The following code assumes for stereo controls the 2338 * first path (when 'found == 0') is the left channel, 2339 * and all remaining paths (when 'found == 1') are the 2340 * right channel. 2341 * 2342 * A stereo control is signified by a valid 'rconnect' 2343 * value, either 0 for unconnected, or >= 0 for connected. 2344 * This is chosen instead of using snd_soc_volsw_is_stereo, 2345 * so that the behavior of snd_soc_dapm_mixer_update_power 2346 * doesn't change even when the kcontrol passed in is 2347 * stereo. 2348 * 2349 * It passes 'connect' as the path connect status for 2350 * the left channel, and 'rconnect' for the right 2351 * channel. 2352 */ 2353 if (found && rconnect >= 0) 2354 soc_dapm_connect_path(path, rconnect, "mixer update"); 2355 else 2356 soc_dapm_connect_path(path, connect, "mixer update"); 2357 found = 1; 2358 } 2359 2360 if (found) 2361 dapm_power_widgets(card, SND_SOC_DAPM_STREAM_NOP); 2362 2363 return found; 2364} 2365 2366int snd_soc_dapm_mixer_update_power(struct snd_soc_dapm_context *dapm, 2367 struct snd_kcontrol *kcontrol, int connect, 2368 struct snd_soc_dapm_update *update) 2369{ 2370 struct snd_soc_card *card = dapm->card; 2371 int ret; 2372 2373 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 2374 card->update = update; 2375 ret = soc_dapm_mixer_update_power(card, kcontrol, connect, -1); 2376 card->update = NULL; 2377 mutex_unlock(&card->dapm_mutex); 2378 if (ret > 0) 2379 snd_soc_dpcm_runtime_update(card); 2380 return ret; 2381} 2382EXPORT_SYMBOL_GPL(snd_soc_dapm_mixer_update_power); 2383 2384static ssize_t dapm_widget_show_component(struct snd_soc_component *cmpnt, 2385 char *buf) 2386{ 2387 struct snd_soc_dapm_context *dapm = snd_soc_component_get_dapm(cmpnt); 2388 struct snd_soc_dapm_widget *w; 2389 int count = 0; 2390 char *state = "not set"; 2391 2392 /* card won't be set for the dummy component, as a spot fix 2393 * we're checking for that case specifically here but in future 2394 * we will ensure that the dummy component looks like others. 2395 */ 2396 if (!cmpnt->card) 2397 return 0; 2398 2399 for_each_card_widgets(cmpnt->card, w) { 2400 if (w->dapm != dapm) 2401 continue; 2402 2403 /* only display widgets that burn power */ 2404 switch (w->id) { 2405 case snd_soc_dapm_hp: 2406 case snd_soc_dapm_mic: 2407 case snd_soc_dapm_spk: 2408 case snd_soc_dapm_line: 2409 case snd_soc_dapm_micbias: 2410 case snd_soc_dapm_dac: 2411 case snd_soc_dapm_adc: 2412 case snd_soc_dapm_pga: 2413 case snd_soc_dapm_effect: 2414 case snd_soc_dapm_out_drv: 2415 case snd_soc_dapm_mixer: 2416 case snd_soc_dapm_mixer_named_ctl: 2417 case snd_soc_dapm_supply: 2418 case snd_soc_dapm_regulator_supply: 2419 case snd_soc_dapm_pinctrl: 2420 case snd_soc_dapm_clock_supply: 2421 if (w->name) 2422 count += sprintf(buf + count, "%s: %s\n", 2423 w->name, w->power ? "On":"Off"); 2424 break; 2425 default: 2426 break; 2427 } 2428 } 2429 2430 switch (snd_soc_dapm_get_bias_level(dapm)) { 2431 case SND_SOC_BIAS_ON: 2432 state = "On"; 2433 break; 2434 case SND_SOC_BIAS_PREPARE: 2435 state = "Prepare"; 2436 break; 2437 case SND_SOC_BIAS_STANDBY: 2438 state = "Standby"; 2439 break; 2440 case SND_SOC_BIAS_OFF: 2441 state = "Off"; 2442 break; 2443 } 2444 count += sprintf(buf + count, "PM State: %s\n", state); 2445 2446 return count; 2447} 2448 2449/* show dapm widget status in sys fs */ 2450static ssize_t dapm_widget_show(struct device *dev, 2451 struct device_attribute *attr, char *buf) 2452{ 2453 struct snd_soc_pcm_runtime *rtd = dev_get_drvdata(dev); 2454 struct snd_soc_dai *codec_dai; 2455 int i, count = 0; 2456 2457 mutex_lock(&rtd->card->dapm_mutex); 2458 2459 for_each_rtd_codec_dais(rtd, i, codec_dai) { 2460 struct snd_soc_component *cmpnt = codec_dai->component; 2461 2462 count += dapm_widget_show_component(cmpnt, buf + count); 2463 } 2464 2465 mutex_unlock(&rtd->card->dapm_mutex); 2466 2467 return count; 2468} 2469 2470static DEVICE_ATTR_RO(dapm_widget); 2471 2472struct attribute *soc_dapm_dev_attrs[] = { 2473 &dev_attr_dapm_widget.attr, 2474 NULL 2475}; 2476 2477static void dapm_free_path(struct snd_soc_dapm_path *path) 2478{ 2479 list_del(&path->list_node[SND_SOC_DAPM_DIR_IN]); 2480 list_del(&path->list_node[SND_SOC_DAPM_DIR_OUT]); 2481 list_del(&path->list_kcontrol); 2482 list_del(&path->list); 2483 kfree(path); 2484} 2485 2486void snd_soc_dapm_free_widget(struct snd_soc_dapm_widget *w) 2487{ 2488 struct snd_soc_dapm_path *p, *next_p; 2489 enum snd_soc_dapm_direction dir; 2490 2491 list_del(&w->list); 2492 list_del(&w->dirty); 2493 /* 2494 * remove source and sink paths associated to this widget. 2495 * While removing the path, remove reference to it from both 2496 * source and sink widgets so that path is removed only once. 2497 */ 2498 snd_soc_dapm_for_each_direction(dir) { 2499 snd_soc_dapm_widget_for_each_path_safe(w, dir, p, next_p) 2500 dapm_free_path(p); 2501 } 2502 2503 kfree(w->kcontrols); 2504 kfree_const(w->name); 2505 kfree_const(w->sname); 2506 kfree(w); 2507} 2508 2509void snd_soc_dapm_reset_cache(struct snd_soc_dapm_context *dapm) 2510{ 2511 dapm->path_sink_cache.widget = NULL; 2512 dapm->path_source_cache.widget = NULL; 2513} 2514 2515/* free all dapm widgets and resources */ 2516static void dapm_free_widgets(struct snd_soc_dapm_context *dapm) 2517{ 2518 struct snd_soc_dapm_widget *w, *next_w; 2519 2520 for_each_card_widgets_safe(dapm->card, w, next_w) { 2521 if (w->dapm != dapm) 2522 continue; 2523 snd_soc_dapm_free_widget(w); 2524 } 2525 snd_soc_dapm_reset_cache(dapm); 2526} 2527 2528static struct snd_soc_dapm_widget *dapm_find_widget( 2529 struct snd_soc_dapm_context *dapm, const char *pin, 2530 bool search_other_contexts) 2531{ 2532 struct snd_soc_dapm_widget *w; 2533 struct snd_soc_dapm_widget *fallback = NULL; 2534 char prefixed_pin[80]; 2535 const char *pin_name; 2536 const char *prefix = soc_dapm_prefix(dapm); 2537 2538 if (prefix) { 2539 snprintf(prefixed_pin, sizeof(prefixed_pin), "%s %s", 2540 prefix, pin); 2541 pin_name = prefixed_pin; 2542 } else { 2543 pin_name = pin; 2544 } 2545 2546 for_each_card_widgets(dapm->card, w) { 2547 if (!strcmp(w->name, pin_name)) { 2548 if (w->dapm == dapm) 2549 return w; 2550 else 2551 fallback = w; 2552 } 2553 } 2554 2555 if (search_other_contexts) 2556 return fallback; 2557 2558 return NULL; 2559} 2560 2561/* 2562 * set the DAPM pin status: 2563 * returns 1 when the value has been updated, 0 when unchanged, or a negative 2564 * error code; called from kcontrol put callback 2565 */ 2566static int __snd_soc_dapm_set_pin(struct snd_soc_dapm_context *dapm, 2567 const char *pin, int status) 2568{ 2569 struct snd_soc_dapm_widget *w = dapm_find_widget(dapm, pin, true); 2570 int ret = 0; 2571 2572 dapm_assert_locked(dapm); 2573 2574 if (!w) { 2575 dev_err(dapm->dev, "ASoC: DAPM unknown pin %s\n", pin); 2576 return -EINVAL; 2577 } 2578 2579 if (w->connected != status) { 2580 dapm_mark_dirty(w, "pin configuration"); 2581 dapm_widget_invalidate_input_paths(w); 2582 dapm_widget_invalidate_output_paths(w); 2583 ret = 1; 2584 } 2585 2586 w->connected = status; 2587 if (status == 0) 2588 w->force = 0; 2589 2590 return ret; 2591} 2592 2593/* 2594 * similar as __snd_soc_dapm_set_pin(), but returns 0 when successful; 2595 * called from several API functions below 2596 */ 2597static int snd_soc_dapm_set_pin(struct snd_soc_dapm_context *dapm, 2598 const char *pin, int status) 2599{ 2600 int ret = __snd_soc_dapm_set_pin(dapm, pin, status); 2601 2602 return ret < 0 ? ret : 0; 2603} 2604 2605/** 2606 * snd_soc_dapm_sync_unlocked - scan and power dapm paths 2607 * @dapm: DAPM context 2608 * 2609 * Walks all dapm audio paths and powers widgets according to their 2610 * stream or path usage. 2611 * 2612 * Requires external locking. 2613 * 2614 * Returns 0 for success. 2615 */ 2616int snd_soc_dapm_sync_unlocked(struct snd_soc_dapm_context *dapm) 2617{ 2618 /* 2619 * Suppress early reports (eg, jacks syncing their state) to avoid 2620 * silly DAPM runs during card startup. 2621 */ 2622 if (!dapm->card || !dapm->card->instantiated) 2623 return 0; 2624 2625 return dapm_power_widgets(dapm->card, SND_SOC_DAPM_STREAM_NOP); 2626} 2627EXPORT_SYMBOL_GPL(snd_soc_dapm_sync_unlocked); 2628 2629/** 2630 * snd_soc_dapm_sync - scan and power dapm paths 2631 * @dapm: DAPM context 2632 * 2633 * Walks all dapm audio paths and powers widgets according to their 2634 * stream or path usage. 2635 * 2636 * Returns 0 for success. 2637 */ 2638int snd_soc_dapm_sync(struct snd_soc_dapm_context *dapm) 2639{ 2640 int ret; 2641 2642 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 2643 ret = snd_soc_dapm_sync_unlocked(dapm); 2644 mutex_unlock(&dapm->card->dapm_mutex); 2645 return ret; 2646} 2647EXPORT_SYMBOL_GPL(snd_soc_dapm_sync); 2648 2649static int dapm_update_dai_chan(struct snd_soc_dapm_path *p, 2650 struct snd_soc_dapm_widget *w, 2651 int channels) 2652{ 2653 switch (w->id) { 2654 case snd_soc_dapm_aif_out: 2655 case snd_soc_dapm_aif_in: 2656 break; 2657 default: 2658 return 0; 2659 } 2660 2661 dev_dbg(w->dapm->dev, "%s DAI route %s -> %s\n", 2662 w->channel < channels ? "Connecting" : "Disconnecting", 2663 p->source->name, p->sink->name); 2664 2665 if (w->channel < channels) 2666 soc_dapm_connect_path(p, true, "dai update"); 2667 else 2668 soc_dapm_connect_path(p, false, "dai update"); 2669 2670 return 0; 2671} 2672 2673static int dapm_update_dai_unlocked(struct snd_pcm_substream *substream, 2674 struct snd_pcm_hw_params *params, 2675 struct snd_soc_dai *dai) 2676{ 2677 int dir = substream->stream; 2678 int channels = params_channels(params); 2679 struct snd_soc_dapm_path *p; 2680 struct snd_soc_dapm_widget *w; 2681 int ret; 2682 2683 w = snd_soc_dai_get_widget(dai, dir); 2684 2685 if (!w) 2686 return 0; 2687 2688 dev_dbg(dai->dev, "Update DAI routes for %s %s\n", dai->name, 2689 dir == SNDRV_PCM_STREAM_PLAYBACK ? "playback" : "capture"); 2690 2691 snd_soc_dapm_widget_for_each_sink_path(w, p) { 2692 ret = dapm_update_dai_chan(p, p->sink, channels); 2693 if (ret < 0) 2694 return ret; 2695 } 2696 2697 snd_soc_dapm_widget_for_each_source_path(w, p) { 2698 ret = dapm_update_dai_chan(p, p->source, channels); 2699 if (ret < 0) 2700 return ret; 2701 } 2702 2703 return 0; 2704} 2705 2706int snd_soc_dapm_update_dai(struct snd_pcm_substream *substream, 2707 struct snd_pcm_hw_params *params, 2708 struct snd_soc_dai *dai) 2709{ 2710 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream); 2711 int ret; 2712 2713 mutex_lock_nested(&rtd->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 2714 ret = dapm_update_dai_unlocked(substream, params, dai); 2715 mutex_unlock(&rtd->card->dapm_mutex); 2716 2717 return ret; 2718} 2719EXPORT_SYMBOL_GPL(snd_soc_dapm_update_dai); 2720 2721/* 2722 * dapm_update_widget_flags() - Re-compute widget sink and source flags 2723 * @w: The widget for which to update the flags 2724 * 2725 * Some widgets have a dynamic category which depends on which neighbors they 2726 * are connected to. This function update the category for these widgets. 2727 * 2728 * This function must be called whenever a path is added or removed to a widget. 2729 */ 2730static void dapm_update_widget_flags(struct snd_soc_dapm_widget *w) 2731{ 2732 enum snd_soc_dapm_direction dir; 2733 struct snd_soc_dapm_path *p; 2734 unsigned int ep; 2735 2736 switch (w->id) { 2737 case snd_soc_dapm_input: 2738 /* On a fully routed card an input is never a source */ 2739 if (w->dapm->card->fully_routed) 2740 return; 2741 ep = SND_SOC_DAPM_EP_SOURCE; 2742 snd_soc_dapm_widget_for_each_source_path(w, p) { 2743 if (p->source->id == snd_soc_dapm_micbias || 2744 p->source->id == snd_soc_dapm_mic || 2745 p->source->id == snd_soc_dapm_line || 2746 p->source->id == snd_soc_dapm_output) { 2747 ep = 0; 2748 break; 2749 } 2750 } 2751 break; 2752 case snd_soc_dapm_output: 2753 /* On a fully routed card a output is never a sink */ 2754 if (w->dapm->card->fully_routed) 2755 return; 2756 ep = SND_SOC_DAPM_EP_SINK; 2757 snd_soc_dapm_widget_for_each_sink_path(w, p) { 2758 if (p->sink->id == snd_soc_dapm_spk || 2759 p->sink->id == snd_soc_dapm_hp || 2760 p->sink->id == snd_soc_dapm_line || 2761 p->sink->id == snd_soc_dapm_input) { 2762 ep = 0; 2763 break; 2764 } 2765 } 2766 break; 2767 case snd_soc_dapm_line: 2768 ep = 0; 2769 snd_soc_dapm_for_each_direction(dir) { 2770 if (!list_empty(&w->edges[dir])) 2771 ep |= SND_SOC_DAPM_DIR_TO_EP(dir); 2772 } 2773 break; 2774 default: 2775 return; 2776 } 2777 2778 w->is_ep = ep; 2779} 2780 2781static int snd_soc_dapm_check_dynamic_path(struct snd_soc_dapm_context *dapm, 2782 struct snd_soc_dapm_widget *source, struct snd_soc_dapm_widget *sink, 2783 const char *control) 2784{ 2785 bool dynamic_source = false; 2786 bool dynamic_sink = false; 2787 2788 if (!control) 2789 return 0; 2790 2791 switch (source->id) { 2792 case snd_soc_dapm_demux: 2793 dynamic_source = true; 2794 break; 2795 default: 2796 break; 2797 } 2798 2799 switch (sink->id) { 2800 case snd_soc_dapm_mux: 2801 case snd_soc_dapm_switch: 2802 case snd_soc_dapm_mixer: 2803 case snd_soc_dapm_mixer_named_ctl: 2804 dynamic_sink = true; 2805 break; 2806 default: 2807 break; 2808 } 2809 2810 if (dynamic_source && dynamic_sink) { 2811 dev_err(dapm->dev, 2812 "Direct connection between demux and mixer/mux not supported for path %s -> [%s] -> %s\n", 2813 source->name, control, sink->name); 2814 return -EINVAL; 2815 } else if (!dynamic_source && !dynamic_sink) { 2816 dev_err(dapm->dev, 2817 "Control not supported for path %s -> [%s] -> %s\n", 2818 source->name, control, sink->name); 2819 return -EINVAL; 2820 } 2821 2822 return 0; 2823} 2824 2825static int snd_soc_dapm_add_path(struct snd_soc_dapm_context *dapm, 2826 struct snd_soc_dapm_widget *wsource, struct snd_soc_dapm_widget *wsink, 2827 const char *control, 2828 int (*connected)(struct snd_soc_dapm_widget *source, 2829 struct snd_soc_dapm_widget *sink)) 2830{ 2831 struct snd_soc_dapm_widget *widgets[2]; 2832 enum snd_soc_dapm_direction dir; 2833 struct snd_soc_dapm_path *path; 2834 int ret; 2835 2836 if (wsink->is_supply && !wsource->is_supply) { 2837 dev_err(dapm->dev, 2838 "Connecting non-supply widget to supply widget is not supported (%s -> %s)\n", 2839 wsource->name, wsink->name); 2840 return -EINVAL; 2841 } 2842 2843 if (connected && !wsource->is_supply) { 2844 dev_err(dapm->dev, 2845 "connected() callback only supported for supply widgets (%s -> %s)\n", 2846 wsource->name, wsink->name); 2847 return -EINVAL; 2848 } 2849 2850 if (wsource->is_supply && control) { 2851 dev_err(dapm->dev, 2852 "Conditional paths are not supported for supply widgets (%s -> [%s] -> %s)\n", 2853 wsource->name, control, wsink->name); 2854 return -EINVAL; 2855 } 2856 2857 ret = snd_soc_dapm_check_dynamic_path(dapm, wsource, wsink, control); 2858 if (ret) 2859 return ret; 2860 2861 path = kzalloc(sizeof(struct snd_soc_dapm_path), GFP_KERNEL); 2862 if (!path) 2863 return -ENOMEM; 2864 2865 path->node[SND_SOC_DAPM_DIR_IN] = wsource; 2866 path->node[SND_SOC_DAPM_DIR_OUT] = wsink; 2867 widgets[SND_SOC_DAPM_DIR_IN] = wsource; 2868 widgets[SND_SOC_DAPM_DIR_OUT] = wsink; 2869 2870 path->connected = connected; 2871 INIT_LIST_HEAD(&path->list); 2872 INIT_LIST_HEAD(&path->list_kcontrol); 2873 2874 if (wsource->is_supply || wsink->is_supply) 2875 path->is_supply = 1; 2876 2877 /* connect static paths */ 2878 if (control == NULL) { 2879 path->connect = 1; 2880 } else { 2881 switch (wsource->id) { 2882 case snd_soc_dapm_demux: 2883 ret = dapm_connect_mux(dapm, path, control, wsource); 2884 if (ret) 2885 goto err; 2886 break; 2887 default: 2888 break; 2889 } 2890 2891 switch (wsink->id) { 2892 case snd_soc_dapm_mux: 2893 ret = dapm_connect_mux(dapm, path, control, wsink); 2894 if (ret != 0) 2895 goto err; 2896 break; 2897 case snd_soc_dapm_switch: 2898 case snd_soc_dapm_mixer: 2899 case snd_soc_dapm_mixer_named_ctl: 2900 ret = dapm_connect_mixer(dapm, path, control); 2901 if (ret != 0) 2902 goto err; 2903 break; 2904 default: 2905 break; 2906 } 2907 } 2908 2909 list_add(&path->list, &dapm->card->paths); 2910 snd_soc_dapm_for_each_direction(dir) 2911 list_add(&path->list_node[dir], &widgets[dir]->edges[dir]); 2912 2913 snd_soc_dapm_for_each_direction(dir) { 2914 dapm_update_widget_flags(widgets[dir]); 2915 dapm_mark_dirty(widgets[dir], "Route added"); 2916 } 2917 2918 if (dapm->card->instantiated && path->connect) 2919 dapm_path_invalidate(path); 2920 2921 return 0; 2922err: 2923 kfree(path); 2924 return ret; 2925} 2926 2927static int snd_soc_dapm_add_route(struct snd_soc_dapm_context *dapm, 2928 const struct snd_soc_dapm_route *route) 2929{ 2930 struct snd_soc_dapm_widget *wsource = NULL, *wsink = NULL, *w; 2931 struct snd_soc_dapm_widget *wtsource = NULL, *wtsink = NULL; 2932 const char *sink; 2933 const char *source; 2934 char prefixed_sink[80]; 2935 char prefixed_source[80]; 2936 const char *prefix; 2937 unsigned int sink_ref = 0; 2938 unsigned int source_ref = 0; 2939 int ret; 2940 2941 prefix = soc_dapm_prefix(dapm); 2942 if (prefix) { 2943 snprintf(prefixed_sink, sizeof(prefixed_sink), "%s %s", 2944 prefix, route->sink); 2945 sink = prefixed_sink; 2946 snprintf(prefixed_source, sizeof(prefixed_source), "%s %s", 2947 prefix, route->source); 2948 source = prefixed_source; 2949 } else { 2950 sink = route->sink; 2951 source = route->source; 2952 } 2953 2954 wsource = dapm_wcache_lookup(&dapm->path_source_cache, source); 2955 wsink = dapm_wcache_lookup(&dapm->path_sink_cache, sink); 2956 2957 if (wsink && wsource) 2958 goto skip_search; 2959 2960 /* 2961 * find src and dest widgets over all widgets but favor a widget from 2962 * current DAPM context 2963 */ 2964 for_each_card_widgets(dapm->card, w) { 2965 if (!wsink && !(strcmp(w->name, sink))) { 2966 wtsink = w; 2967 if (w->dapm == dapm) { 2968 wsink = w; 2969 if (wsource) 2970 break; 2971 } 2972 sink_ref++; 2973 if (sink_ref > 1) 2974 dev_warn(dapm->dev, 2975 "ASoC: sink widget %s overwritten\n", 2976 w->name); 2977 continue; 2978 } 2979 if (!wsource && !(strcmp(w->name, source))) { 2980 wtsource = w; 2981 if (w->dapm == dapm) { 2982 wsource = w; 2983 if (wsink) 2984 break; 2985 } 2986 source_ref++; 2987 if (source_ref > 1) 2988 dev_warn(dapm->dev, 2989 "ASoC: source widget %s overwritten\n", 2990 w->name); 2991 } 2992 } 2993 /* use widget from another DAPM context if not found from this */ 2994 if (!wsink) 2995 wsink = wtsink; 2996 if (!wsource) 2997 wsource = wtsource; 2998 2999 if (wsource == NULL) { 3000 dev_err(dapm->dev, "ASoC: no source widget found for %s\n", 3001 route->source); 3002 return -ENODEV; 3003 } 3004 if (wsink == NULL) { 3005 dev_err(dapm->dev, "ASoC: no sink widget found for %s\n", 3006 route->sink); 3007 return -ENODEV; 3008 } 3009 3010skip_search: 3011 dapm_wcache_update(&dapm->path_sink_cache, wsink); 3012 dapm_wcache_update(&dapm->path_source_cache, wsource); 3013 3014 ret = snd_soc_dapm_add_path(dapm, wsource, wsink, route->control, 3015 route->connected); 3016 if (ret) 3017 goto err; 3018 3019 return 0; 3020err: 3021 dev_warn(dapm->dev, "ASoC: no dapm match for %s --> %s --> %s\n", 3022 source, route->control, sink); 3023 return ret; 3024} 3025 3026static int snd_soc_dapm_del_route(struct snd_soc_dapm_context *dapm, 3027 const struct snd_soc_dapm_route *route) 3028{ 3029 struct snd_soc_dapm_widget *wsource, *wsink; 3030 struct snd_soc_dapm_path *path, *p; 3031 const char *sink; 3032 const char *source; 3033 char prefixed_sink[80]; 3034 char prefixed_source[80]; 3035 const char *prefix; 3036 3037 if (route->control) { 3038 dev_err(dapm->dev, 3039 "ASoC: Removal of routes with controls not supported\n"); 3040 return -EINVAL; 3041 } 3042 3043 prefix = soc_dapm_prefix(dapm); 3044 if (prefix) { 3045 snprintf(prefixed_sink, sizeof(prefixed_sink), "%s %s", 3046 prefix, route->sink); 3047 sink = prefixed_sink; 3048 snprintf(prefixed_source, sizeof(prefixed_source), "%s %s", 3049 prefix, route->source); 3050 source = prefixed_source; 3051 } else { 3052 sink = route->sink; 3053 source = route->source; 3054 } 3055 3056 path = NULL; 3057 list_for_each_entry(p, &dapm->card->paths, list) { 3058 if (strcmp(p->source->name, source) != 0) 3059 continue; 3060 if (strcmp(p->sink->name, sink) != 0) 3061 continue; 3062 path = p; 3063 break; 3064 } 3065 3066 if (path) { 3067 wsource = path->source; 3068 wsink = path->sink; 3069 3070 dapm_mark_dirty(wsource, "Route removed"); 3071 dapm_mark_dirty(wsink, "Route removed"); 3072 if (path->connect) 3073 dapm_path_invalidate(path); 3074 3075 dapm_free_path(path); 3076 3077 /* Update any path related flags */ 3078 dapm_update_widget_flags(wsource); 3079 dapm_update_widget_flags(wsink); 3080 } else { 3081 dev_warn(dapm->dev, "ASoC: Route %s->%s does not exist\n", 3082 source, sink); 3083 } 3084 3085 return 0; 3086} 3087 3088/** 3089 * snd_soc_dapm_add_routes - Add routes between DAPM widgets 3090 * @dapm: DAPM context 3091 * @route: audio routes 3092 * @num: number of routes 3093 * 3094 * Connects 2 dapm widgets together via a named audio path. The sink is 3095 * the widget receiving the audio signal, whilst the source is the sender 3096 * of the audio signal. 3097 * 3098 * Returns 0 for success else error. On error all resources can be freed 3099 * with a call to snd_soc_card_free(). 3100 */ 3101int snd_soc_dapm_add_routes(struct snd_soc_dapm_context *dapm, 3102 const struct snd_soc_dapm_route *route, int num) 3103{ 3104 int i, r, ret = 0; 3105 3106 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3107 for (i = 0; i < num; i++) { 3108 r = snd_soc_dapm_add_route(dapm, route); 3109 if (r < 0) { 3110 dev_err(dapm->dev, "ASoC: Failed to add route %s -> %s -> %s\n", 3111 route->source, 3112 route->control ? route->control : "direct", 3113 route->sink); 3114 ret = r; 3115 } 3116 route++; 3117 } 3118 mutex_unlock(&dapm->card->dapm_mutex); 3119 3120 return ret; 3121} 3122EXPORT_SYMBOL_GPL(snd_soc_dapm_add_routes); 3123 3124/** 3125 * snd_soc_dapm_del_routes - Remove routes between DAPM widgets 3126 * @dapm: DAPM context 3127 * @route: audio routes 3128 * @num: number of routes 3129 * 3130 * Removes routes from the DAPM context. 3131 */ 3132int snd_soc_dapm_del_routes(struct snd_soc_dapm_context *dapm, 3133 const struct snd_soc_dapm_route *route, int num) 3134{ 3135 int i; 3136 3137 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3138 for (i = 0; i < num; i++) { 3139 snd_soc_dapm_del_route(dapm, route); 3140 route++; 3141 } 3142 mutex_unlock(&dapm->card->dapm_mutex); 3143 3144 return 0; 3145} 3146EXPORT_SYMBOL_GPL(snd_soc_dapm_del_routes); 3147 3148static int snd_soc_dapm_weak_route(struct snd_soc_dapm_context *dapm, 3149 const struct snd_soc_dapm_route *route) 3150{ 3151 struct snd_soc_dapm_widget *source = dapm_find_widget(dapm, 3152 route->source, 3153 true); 3154 struct snd_soc_dapm_widget *sink = dapm_find_widget(dapm, 3155 route->sink, 3156 true); 3157 struct snd_soc_dapm_path *path; 3158 int count = 0; 3159 3160 if (!source) { 3161 dev_err(dapm->dev, "ASoC: Unable to find source %s for weak route\n", 3162 route->source); 3163 return -ENODEV; 3164 } 3165 3166 if (!sink) { 3167 dev_err(dapm->dev, "ASoC: Unable to find sink %s for weak route\n", 3168 route->sink); 3169 return -ENODEV; 3170 } 3171 3172 if (route->control || route->connected) 3173 dev_warn(dapm->dev, "ASoC: Ignoring control for weak route %s->%s\n", 3174 route->source, route->sink); 3175 3176 snd_soc_dapm_widget_for_each_sink_path(source, path) { 3177 if (path->sink == sink) { 3178 path->weak = 1; 3179 count++; 3180 } 3181 } 3182 3183 if (count == 0) 3184 dev_err(dapm->dev, "ASoC: No path found for weak route %s->%s\n", 3185 route->source, route->sink); 3186 if (count > 1) 3187 dev_warn(dapm->dev, "ASoC: %d paths found for weak route %s->%s\n", 3188 count, route->source, route->sink); 3189 3190 return 0; 3191} 3192 3193/** 3194 * snd_soc_dapm_weak_routes - Mark routes between DAPM widgets as weak 3195 * @dapm: DAPM context 3196 * @route: audio routes 3197 * @num: number of routes 3198 * 3199 * Mark existing routes matching those specified in the passed array 3200 * as being weak, meaning that they are ignored for the purpose of 3201 * power decisions. The main intended use case is for sidetone paths 3202 * which couple audio between other independent paths if they are both 3203 * active in order to make the combination work better at the user 3204 * level but which aren't intended to be "used". 3205 * 3206 * Note that CODEC drivers should not use this as sidetone type paths 3207 * can frequently also be used as bypass paths. 3208 */ 3209int snd_soc_dapm_weak_routes(struct snd_soc_dapm_context *dapm, 3210 const struct snd_soc_dapm_route *route, int num) 3211{ 3212 int i, err; 3213 int ret = 0; 3214 3215 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_INIT); 3216 for (i = 0; i < num; i++) { 3217 err = snd_soc_dapm_weak_route(dapm, route); 3218 if (err) 3219 ret = err; 3220 route++; 3221 } 3222 mutex_unlock(&dapm->card->dapm_mutex); 3223 3224 return ret; 3225} 3226EXPORT_SYMBOL_GPL(snd_soc_dapm_weak_routes); 3227 3228/** 3229 * snd_soc_dapm_new_widgets - add new dapm widgets 3230 * @card: card to be checked for new dapm widgets 3231 * 3232 * Checks the codec for any new dapm widgets and creates them if found. 3233 * 3234 * Returns 0 for success. 3235 */ 3236int snd_soc_dapm_new_widgets(struct snd_soc_card *card) 3237{ 3238 struct snd_soc_dapm_widget *w; 3239 unsigned int val; 3240 3241 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_INIT); 3242 3243 for_each_card_widgets(card, w) 3244 { 3245 if (w->new) 3246 continue; 3247 3248 if (w->num_kcontrols) { 3249 w->kcontrols = kcalloc(w->num_kcontrols, 3250 sizeof(struct snd_kcontrol *), 3251 GFP_KERNEL); 3252 if (!w->kcontrols) { 3253 mutex_unlock(&card->dapm_mutex); 3254 return -ENOMEM; 3255 } 3256 } 3257 3258 switch(w->id) { 3259 case snd_soc_dapm_switch: 3260 case snd_soc_dapm_mixer: 3261 case snd_soc_dapm_mixer_named_ctl: 3262 dapm_new_mixer(w); 3263 break; 3264 case snd_soc_dapm_mux: 3265 case snd_soc_dapm_demux: 3266 dapm_new_mux(w); 3267 break; 3268 case snd_soc_dapm_pga: 3269 case snd_soc_dapm_effect: 3270 case snd_soc_dapm_out_drv: 3271 dapm_new_pga(w); 3272 break; 3273 case snd_soc_dapm_dai_link: 3274 dapm_new_dai_link(w); 3275 break; 3276 default: 3277 break; 3278 } 3279 3280 /* Read the initial power state from the device */ 3281 if (w->reg >= 0) { 3282 val = soc_dapm_read(w->dapm, w->reg); 3283 val = val >> w->shift; 3284 val &= w->mask; 3285 if (val == w->on_val) 3286 w->power = 1; 3287 } 3288 3289 w->new = 1; 3290 3291 dapm_mark_dirty(w, "new widget"); 3292 dapm_debugfs_add_widget(w); 3293 } 3294 3295 dapm_power_widgets(card, SND_SOC_DAPM_STREAM_NOP); 3296 mutex_unlock(&card->dapm_mutex); 3297 return 0; 3298} 3299EXPORT_SYMBOL_GPL(snd_soc_dapm_new_widgets); 3300 3301/** 3302 * snd_soc_dapm_get_volsw - dapm mixer get callback 3303 * @kcontrol: mixer control 3304 * @ucontrol: control element information 3305 * 3306 * Callback to get the value of a dapm mixer control. 3307 * 3308 * Returns 0 for success. 3309 */ 3310int snd_soc_dapm_get_volsw(struct snd_kcontrol *kcontrol, 3311 struct snd_ctl_elem_value *ucontrol) 3312{ 3313 struct snd_soc_dapm_context *dapm = snd_soc_dapm_kcontrol_dapm(kcontrol); 3314 struct snd_soc_card *card = dapm->card; 3315 struct soc_mixer_control *mc = 3316 (struct soc_mixer_control *)kcontrol->private_value; 3317 int reg = mc->reg; 3318 unsigned int shift = mc->shift; 3319 int max = mc->max; 3320 unsigned int width = fls(max); 3321 unsigned int mask = (1 << fls(max)) - 1; 3322 unsigned int invert = mc->invert; 3323 unsigned int reg_val, val, rval = 0; 3324 3325 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3326 if (dapm_kcontrol_is_powered(kcontrol) && reg != SND_SOC_NOPM) { 3327 reg_val = soc_dapm_read(dapm, reg); 3328 val = (reg_val >> shift) & mask; 3329 3330 if (reg != mc->rreg) 3331 reg_val = soc_dapm_read(dapm, mc->rreg); 3332 3333 if (snd_soc_volsw_is_stereo(mc)) 3334 rval = (reg_val >> mc->rshift) & mask; 3335 } else { 3336 reg_val = dapm_kcontrol_get_value(kcontrol); 3337 val = reg_val & mask; 3338 3339 if (snd_soc_volsw_is_stereo(mc)) 3340 rval = (reg_val >> width) & mask; 3341 } 3342 mutex_unlock(&card->dapm_mutex); 3343 3344 if (invert) 3345 ucontrol->value.integer.value[0] = max - val; 3346 else 3347 ucontrol->value.integer.value[0] = val; 3348 3349 if (snd_soc_volsw_is_stereo(mc)) { 3350 if (invert) 3351 ucontrol->value.integer.value[1] = max - rval; 3352 else 3353 ucontrol->value.integer.value[1] = rval; 3354 } 3355 3356 return 0; 3357} 3358EXPORT_SYMBOL_GPL(snd_soc_dapm_get_volsw); 3359 3360/** 3361 * snd_soc_dapm_put_volsw - dapm mixer set callback 3362 * @kcontrol: mixer control 3363 * @ucontrol: control element information 3364 * 3365 * Callback to set the value of a dapm mixer control. 3366 * 3367 * Returns 0 for success. 3368 */ 3369int snd_soc_dapm_put_volsw(struct snd_kcontrol *kcontrol, 3370 struct snd_ctl_elem_value *ucontrol) 3371{ 3372 struct snd_soc_dapm_context *dapm = snd_soc_dapm_kcontrol_dapm(kcontrol); 3373 struct snd_soc_card *card = dapm->card; 3374 struct soc_mixer_control *mc = 3375 (struct soc_mixer_control *)kcontrol->private_value; 3376 int reg = mc->reg; 3377 unsigned int shift = mc->shift; 3378 int max = mc->max; 3379 unsigned int width = fls(max); 3380 unsigned int mask = (1 << width) - 1; 3381 unsigned int invert = mc->invert; 3382 unsigned int val, rval = 0; 3383 int connect, rconnect = -1, change, reg_change = 0; 3384 struct snd_soc_dapm_update update = {}; 3385 int ret = 0; 3386 3387 val = (ucontrol->value.integer.value[0] & mask); 3388 connect = !!val; 3389 3390 if (invert) 3391 val = max - val; 3392 3393 if (snd_soc_volsw_is_stereo(mc)) { 3394 rval = (ucontrol->value.integer.value[1] & mask); 3395 rconnect = !!rval; 3396 if (invert) 3397 rval = max - rval; 3398 } 3399 3400 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3401 3402 /* This assumes field width < (bits in unsigned int / 2) */ 3403 if (width > sizeof(unsigned int) * 8 / 2) 3404 dev_warn(dapm->dev, 3405 "ASoC: control %s field width limit exceeded\n", 3406 kcontrol->id.name); 3407 change = dapm_kcontrol_set_value(kcontrol, val | (rval << width)); 3408 3409 if (reg != SND_SOC_NOPM) { 3410 val = val << shift; 3411 rval = rval << mc->rshift; 3412 3413 reg_change = soc_dapm_test_bits(dapm, reg, mask << shift, val); 3414 3415 if (snd_soc_volsw_is_stereo(mc)) 3416 reg_change |= soc_dapm_test_bits(dapm, mc->rreg, 3417 mask << mc->rshift, 3418 rval); 3419 } 3420 3421 if (change || reg_change) { 3422 if (reg_change) { 3423 if (snd_soc_volsw_is_stereo(mc)) { 3424 update.has_second_set = true; 3425 update.reg2 = mc->rreg; 3426 update.mask2 = mask << mc->rshift; 3427 update.val2 = rval; 3428 } 3429 update.kcontrol = kcontrol; 3430 update.reg = reg; 3431 update.mask = mask << shift; 3432 update.val = val; 3433 card->update = &update; 3434 } 3435 3436 ret = soc_dapm_mixer_update_power(card, kcontrol, connect, 3437 rconnect); 3438 3439 card->update = NULL; 3440 } 3441 3442 mutex_unlock(&card->dapm_mutex); 3443 3444 if (ret > 0) 3445 snd_soc_dpcm_runtime_update(card); 3446 3447 return change; 3448} 3449EXPORT_SYMBOL_GPL(snd_soc_dapm_put_volsw); 3450 3451/** 3452 * snd_soc_dapm_get_enum_double - dapm enumerated double mixer get callback 3453 * @kcontrol: mixer control 3454 * @ucontrol: control element information 3455 * 3456 * Callback to get the value of a dapm enumerated double mixer control. 3457 * 3458 * Returns 0 for success. 3459 */ 3460int snd_soc_dapm_get_enum_double(struct snd_kcontrol *kcontrol, 3461 struct snd_ctl_elem_value *ucontrol) 3462{ 3463 struct snd_soc_dapm_context *dapm = snd_soc_dapm_kcontrol_dapm(kcontrol); 3464 struct snd_soc_card *card = dapm->card; 3465 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 3466 unsigned int reg_val, val; 3467 3468 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3469 if (e->reg != SND_SOC_NOPM && dapm_kcontrol_is_powered(kcontrol)) { 3470 reg_val = soc_dapm_read(dapm, e->reg); 3471 } else { 3472 reg_val = dapm_kcontrol_get_value(kcontrol); 3473 } 3474 mutex_unlock(&card->dapm_mutex); 3475 3476 val = (reg_val >> e->shift_l) & e->mask; 3477 ucontrol->value.enumerated.item[0] = snd_soc_enum_val_to_item(e, val); 3478 if (e->shift_l != e->shift_r) { 3479 val = (reg_val >> e->shift_r) & e->mask; 3480 val = snd_soc_enum_val_to_item(e, val); 3481 ucontrol->value.enumerated.item[1] = val; 3482 } 3483 3484 return 0; 3485} 3486EXPORT_SYMBOL_GPL(snd_soc_dapm_get_enum_double); 3487 3488/** 3489 * snd_soc_dapm_put_enum_double - dapm enumerated double mixer set callback 3490 * @kcontrol: mixer control 3491 * @ucontrol: control element information 3492 * 3493 * Callback to set the value of a dapm enumerated double mixer control. 3494 * 3495 * Returns 0 for success. 3496 */ 3497int snd_soc_dapm_put_enum_double(struct snd_kcontrol *kcontrol, 3498 struct snd_ctl_elem_value *ucontrol) 3499{ 3500 struct snd_soc_dapm_context *dapm = snd_soc_dapm_kcontrol_dapm(kcontrol); 3501 struct snd_soc_card *card = dapm->card; 3502 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 3503 unsigned int *item = ucontrol->value.enumerated.item; 3504 unsigned int val, change, reg_change = 0; 3505 unsigned int mask; 3506 struct snd_soc_dapm_update update = {}; 3507 int ret = 0; 3508 3509 if (item[0] >= e->items) 3510 return -EINVAL; 3511 3512 val = snd_soc_enum_item_to_val(e, item[0]) << e->shift_l; 3513 mask = e->mask << e->shift_l; 3514 if (e->shift_l != e->shift_r) { 3515 if (item[1] > e->items) 3516 return -EINVAL; 3517 val |= snd_soc_enum_item_to_val(e, item[1]) << e->shift_r; 3518 mask |= e->mask << e->shift_r; 3519 } 3520 3521 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3522 3523 change = dapm_kcontrol_set_value(kcontrol, val); 3524 3525 if (e->reg != SND_SOC_NOPM) 3526 reg_change = soc_dapm_test_bits(dapm, e->reg, mask, val); 3527 3528 if (change || reg_change) { 3529 if (reg_change) { 3530 update.kcontrol = kcontrol; 3531 update.reg = e->reg; 3532 update.mask = mask; 3533 update.val = val; 3534 card->update = &update; 3535 } 3536 3537 ret = soc_dapm_mux_update_power(card, kcontrol, item[0], e); 3538 3539 card->update = NULL; 3540 } 3541 3542 mutex_unlock(&card->dapm_mutex); 3543 3544 if (ret > 0) 3545 snd_soc_dpcm_runtime_update(card); 3546 3547 return change; 3548} 3549EXPORT_SYMBOL_GPL(snd_soc_dapm_put_enum_double); 3550 3551/** 3552 * snd_soc_dapm_info_pin_switch - Info for a pin switch 3553 * 3554 * @kcontrol: mixer control 3555 * @uinfo: control element information 3556 * 3557 * Callback to provide information about a pin switch control. 3558 */ 3559int snd_soc_dapm_info_pin_switch(struct snd_kcontrol *kcontrol, 3560 struct snd_ctl_elem_info *uinfo) 3561{ 3562 uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; 3563 uinfo->count = 1; 3564 uinfo->value.integer.min = 0; 3565 uinfo->value.integer.max = 1; 3566 3567 return 0; 3568} 3569EXPORT_SYMBOL_GPL(snd_soc_dapm_info_pin_switch); 3570 3571/** 3572 * snd_soc_dapm_get_pin_switch - Get information for a pin switch 3573 * 3574 * @kcontrol: mixer control 3575 * @ucontrol: Value 3576 */ 3577int snd_soc_dapm_get_pin_switch(struct snd_kcontrol *kcontrol, 3578 struct snd_ctl_elem_value *ucontrol) 3579{ 3580 struct snd_soc_card *card = snd_kcontrol_chip(kcontrol); 3581 const char *pin = (const char *)kcontrol->private_value; 3582 3583 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3584 3585 ucontrol->value.integer.value[0] = 3586 snd_soc_dapm_get_pin_status(&card->dapm, pin); 3587 3588 mutex_unlock(&card->dapm_mutex); 3589 3590 return 0; 3591} 3592EXPORT_SYMBOL_GPL(snd_soc_dapm_get_pin_switch); 3593 3594/** 3595 * snd_soc_dapm_put_pin_switch - Set information for a pin switch 3596 * 3597 * @kcontrol: mixer control 3598 * @ucontrol: Value 3599 */ 3600int snd_soc_dapm_put_pin_switch(struct snd_kcontrol *kcontrol, 3601 struct snd_ctl_elem_value *ucontrol) 3602{ 3603 struct snd_soc_card *card = snd_kcontrol_chip(kcontrol); 3604 const char *pin = (const char *)kcontrol->private_value; 3605 int ret; 3606 3607 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3608 ret = __snd_soc_dapm_set_pin(&card->dapm, pin, 3609 !!ucontrol->value.integer.value[0]); 3610 mutex_unlock(&card->dapm_mutex); 3611 3612 snd_soc_dapm_sync(&card->dapm); 3613 return ret; 3614} 3615EXPORT_SYMBOL_GPL(snd_soc_dapm_put_pin_switch); 3616 3617struct snd_soc_dapm_widget * 3618snd_soc_dapm_new_control_unlocked(struct snd_soc_dapm_context *dapm, 3619 const struct snd_soc_dapm_widget *widget) 3620{ 3621 enum snd_soc_dapm_direction dir; 3622 struct snd_soc_dapm_widget *w; 3623 const char *prefix; 3624 int ret; 3625 3626 if ((w = dapm_cnew_widget(widget)) == NULL) 3627 return ERR_PTR(-ENOMEM); 3628 3629 switch (w->id) { 3630 case snd_soc_dapm_regulator_supply: 3631 w->regulator = devm_regulator_get(dapm->dev, w->name); 3632 if (IS_ERR(w->regulator)) { 3633 ret = PTR_ERR(w->regulator); 3634 goto request_failed; 3635 } 3636 3637 if (w->on_val & SND_SOC_DAPM_REGULATOR_BYPASS) { 3638 ret = regulator_allow_bypass(w->regulator, true); 3639 if (ret != 0) 3640 dev_warn(dapm->dev, 3641 "ASoC: Failed to bypass %s: %d\n", 3642 w->name, ret); 3643 } 3644 break; 3645 case snd_soc_dapm_pinctrl: 3646 w->pinctrl = devm_pinctrl_get(dapm->dev); 3647 if (IS_ERR(w->pinctrl)) { 3648 ret = PTR_ERR(w->pinctrl); 3649 goto request_failed; 3650 } 3651 3652 /* set to sleep_state when initializing */ 3653 dapm_pinctrl_event(w, NULL, SND_SOC_DAPM_POST_PMD); 3654 break; 3655 case snd_soc_dapm_clock_supply: 3656 w->clk = devm_clk_get(dapm->dev, w->name); 3657 if (IS_ERR(w->clk)) { 3658 ret = PTR_ERR(w->clk); 3659 goto request_failed; 3660 } 3661 break; 3662 default: 3663 break; 3664 } 3665 3666 prefix = soc_dapm_prefix(dapm); 3667 if (prefix) 3668 w->name = kasprintf(GFP_KERNEL, "%s %s", prefix, widget->name); 3669 else 3670 w->name = kstrdup_const(widget->name, GFP_KERNEL); 3671 if (w->name == NULL) { 3672 kfree_const(w->sname); 3673 kfree(w); 3674 return ERR_PTR(-ENOMEM); 3675 } 3676 3677 switch (w->id) { 3678 case snd_soc_dapm_mic: 3679 w->is_ep = SND_SOC_DAPM_EP_SOURCE; 3680 w->power_check = dapm_generic_check_power; 3681 break; 3682 case snd_soc_dapm_input: 3683 if (!dapm->card->fully_routed) 3684 w->is_ep = SND_SOC_DAPM_EP_SOURCE; 3685 w->power_check = dapm_generic_check_power; 3686 break; 3687 case snd_soc_dapm_spk: 3688 case snd_soc_dapm_hp: 3689 w->is_ep = SND_SOC_DAPM_EP_SINK; 3690 w->power_check = dapm_generic_check_power; 3691 break; 3692 case snd_soc_dapm_output: 3693 if (!dapm->card->fully_routed) 3694 w->is_ep = SND_SOC_DAPM_EP_SINK; 3695 w->power_check = dapm_generic_check_power; 3696 break; 3697 case snd_soc_dapm_vmid: 3698 case snd_soc_dapm_siggen: 3699 w->is_ep = SND_SOC_DAPM_EP_SOURCE; 3700 w->power_check = dapm_always_on_check_power; 3701 break; 3702 case snd_soc_dapm_sink: 3703 w->is_ep = SND_SOC_DAPM_EP_SINK; 3704 w->power_check = dapm_always_on_check_power; 3705 break; 3706 3707 case snd_soc_dapm_mux: 3708 case snd_soc_dapm_demux: 3709 case snd_soc_dapm_switch: 3710 case snd_soc_dapm_mixer: 3711 case snd_soc_dapm_mixer_named_ctl: 3712 case snd_soc_dapm_adc: 3713 case snd_soc_dapm_aif_out: 3714 case snd_soc_dapm_dac: 3715 case snd_soc_dapm_aif_in: 3716 case snd_soc_dapm_pga: 3717 case snd_soc_dapm_buffer: 3718 case snd_soc_dapm_scheduler: 3719 case snd_soc_dapm_effect: 3720 case snd_soc_dapm_src: 3721 case snd_soc_dapm_asrc: 3722 case snd_soc_dapm_encoder: 3723 case snd_soc_dapm_decoder: 3724 case snd_soc_dapm_out_drv: 3725 case snd_soc_dapm_micbias: 3726 case snd_soc_dapm_line: 3727 case snd_soc_dapm_dai_link: 3728 case snd_soc_dapm_dai_out: 3729 case snd_soc_dapm_dai_in: 3730 w->power_check = dapm_generic_check_power; 3731 break; 3732 case snd_soc_dapm_supply: 3733 case snd_soc_dapm_regulator_supply: 3734 case snd_soc_dapm_pinctrl: 3735 case snd_soc_dapm_clock_supply: 3736 case snd_soc_dapm_kcontrol: 3737 w->is_supply = 1; 3738 w->power_check = dapm_supply_check_power; 3739 break; 3740 default: 3741 w->power_check = dapm_always_on_check_power; 3742 break; 3743 } 3744 3745 w->dapm = dapm; 3746 INIT_LIST_HEAD(&w->list); 3747 INIT_LIST_HEAD(&w->dirty); 3748 /* see for_each_card_widgets */ 3749 list_add_tail(&w->list, &dapm->card->widgets); 3750 3751 snd_soc_dapm_for_each_direction(dir) { 3752 INIT_LIST_HEAD(&w->edges[dir]); 3753 w->endpoints[dir] = -1; 3754 } 3755 3756 /* machine layer sets up unconnected pins and insertions */ 3757 w->connected = 1; 3758 return w; 3759 3760request_failed: 3761 if (ret != -EPROBE_DEFER) 3762 dev_err(dapm->dev, "ASoC: Failed to request %s: %d\n", 3763 w->name, ret); 3764 3765 kfree_const(w->sname); 3766 kfree(w); 3767 return ERR_PTR(ret); 3768} 3769 3770/** 3771 * snd_soc_dapm_new_control - create new dapm control 3772 * @dapm: DAPM context 3773 * @widget: widget template 3774 * 3775 * Creates new DAPM control based upon a template. 3776 * 3777 * Returns a widget pointer on success or an error pointer on failure 3778 */ 3779struct snd_soc_dapm_widget * 3780snd_soc_dapm_new_control(struct snd_soc_dapm_context *dapm, 3781 const struct snd_soc_dapm_widget *widget) 3782{ 3783 struct snd_soc_dapm_widget *w; 3784 3785 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 3786 w = snd_soc_dapm_new_control_unlocked(dapm, widget); 3787 mutex_unlock(&dapm->card->dapm_mutex); 3788 3789 return w; 3790} 3791EXPORT_SYMBOL_GPL(snd_soc_dapm_new_control); 3792 3793/** 3794 * snd_soc_dapm_new_controls - create new dapm controls 3795 * @dapm: DAPM context 3796 * @widget: widget array 3797 * @num: number of widgets 3798 * 3799 * Creates new DAPM controls based upon the templates. 3800 * 3801 * Returns 0 for success else error. 3802 */ 3803int snd_soc_dapm_new_controls(struct snd_soc_dapm_context *dapm, 3804 const struct snd_soc_dapm_widget *widget, 3805 int num) 3806{ 3807 struct snd_soc_dapm_widget *w; 3808 int i; 3809 int ret = 0; 3810 3811 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_INIT); 3812 for (i = 0; i < num; i++) { 3813 w = snd_soc_dapm_new_control_unlocked(dapm, widget); 3814 if (IS_ERR(w)) { 3815 ret = PTR_ERR(w); 3816 break; 3817 } 3818 widget++; 3819 } 3820 mutex_unlock(&dapm->card->dapm_mutex); 3821 return ret; 3822} 3823EXPORT_SYMBOL_GPL(snd_soc_dapm_new_controls); 3824 3825static int 3826snd_soc_dai_link_event_pre_pmu(struct snd_soc_dapm_widget *w, 3827 struct snd_pcm_substream *substream) 3828{ 3829 struct snd_soc_dapm_path *path; 3830 struct snd_soc_dai *source, *sink; 3831 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream); 3832 struct snd_pcm_hw_params *params = NULL; 3833 const struct snd_soc_pcm_stream *config = NULL; 3834 struct snd_pcm_runtime *runtime = NULL; 3835 unsigned int fmt; 3836 int ret = 0; 3837 3838 params = kzalloc(sizeof(*params), GFP_KERNEL); 3839 if (!params) 3840 return -ENOMEM; 3841 3842 runtime = kzalloc(sizeof(*runtime), GFP_KERNEL); 3843 if (!runtime) { 3844 ret = -ENOMEM; 3845 goto out; 3846 } 3847 3848 substream->runtime = runtime; 3849 3850 substream->stream = SNDRV_PCM_STREAM_CAPTURE; 3851 snd_soc_dapm_widget_for_each_source_path(w, path) { 3852 source = path->source->priv; 3853 3854 ret = snd_soc_dai_startup(source, substream); 3855 if (ret < 0) { 3856 dev_err(source->dev, 3857 "ASoC: startup() failed: %d\n", ret); 3858 goto out; 3859 } 3860 snd_soc_dai_activate(source, substream->stream); 3861 } 3862 3863 substream->stream = SNDRV_PCM_STREAM_PLAYBACK; 3864 snd_soc_dapm_widget_for_each_sink_path(w, path) { 3865 sink = path->sink->priv; 3866 3867 ret = snd_soc_dai_startup(sink, substream); 3868 if (ret < 0) { 3869 dev_err(sink->dev, 3870 "ASoC: startup() failed: %d\n", ret); 3871 goto out; 3872 } 3873 snd_soc_dai_activate(sink, substream->stream); 3874 } 3875 3876 substream->hw_opened = 1; 3877 3878 /* 3879 * Note: getting the config after .startup() gives a chance to 3880 * either party on the link to alter the configuration if 3881 * necessary 3882 */ 3883 config = rtd->dai_link->params + rtd->params_select; 3884 if (WARN_ON(!config)) { 3885 dev_err(w->dapm->dev, "ASoC: link config missing\n"); 3886 ret = -EINVAL; 3887 goto out; 3888 } 3889 3890 /* Be a little careful as we don't want to overflow the mask array */ 3891 if (config->formats) { 3892 fmt = ffs(config->formats) - 1; 3893 } else { 3894 dev_warn(w->dapm->dev, "ASoC: Invalid format %llx specified\n", 3895 config->formats); 3896 3897 ret = -EINVAL; 3898 goto out; 3899 } 3900 3901 snd_mask_set(hw_param_mask(params, SNDRV_PCM_HW_PARAM_FORMAT), fmt); 3902 hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE)->min = 3903 config->rate_min; 3904 hw_param_interval(params, SNDRV_PCM_HW_PARAM_RATE)->max = 3905 config->rate_max; 3906 hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS)->min 3907 = config->channels_min; 3908 hw_param_interval(params, SNDRV_PCM_HW_PARAM_CHANNELS)->max 3909 = config->channels_max; 3910 3911 substream->stream = SNDRV_PCM_STREAM_CAPTURE; 3912 snd_soc_dapm_widget_for_each_source_path(w, path) { 3913 source = path->source->priv; 3914 3915 ret = snd_soc_dai_hw_params(source, substream, params); 3916 if (ret < 0) 3917 goto out; 3918 3919 dapm_update_dai_unlocked(substream, params, source); 3920 } 3921 3922 substream->stream = SNDRV_PCM_STREAM_PLAYBACK; 3923 snd_soc_dapm_widget_for_each_sink_path(w, path) { 3924 sink = path->sink->priv; 3925 3926 ret = snd_soc_dai_hw_params(sink, substream, params); 3927 if (ret < 0) 3928 goto out; 3929 3930 dapm_update_dai_unlocked(substream, params, sink); 3931 } 3932 3933 runtime->format = params_format(params); 3934 runtime->subformat = params_subformat(params); 3935 runtime->channels = params_channels(params); 3936 runtime->rate = params_rate(params); 3937 3938out: 3939 kfree(params); 3940 return ret; 3941} 3942 3943static int snd_soc_dai_link_event(struct snd_soc_dapm_widget *w, 3944 struct snd_kcontrol *kcontrol, int event) 3945{ 3946 struct snd_soc_dapm_path *path; 3947 struct snd_soc_dai *source, *sink; 3948 struct snd_pcm_substream *substream = w->priv; 3949 int ret = 0, saved_stream = substream->stream; 3950 3951 if (WARN_ON(list_empty(&w->edges[SND_SOC_DAPM_DIR_OUT]) || 3952 list_empty(&w->edges[SND_SOC_DAPM_DIR_IN]))) 3953 return -EINVAL; 3954 3955 switch (event) { 3956 case SND_SOC_DAPM_PRE_PMU: 3957 ret = snd_soc_dai_link_event_pre_pmu(w, substream); 3958 if (ret < 0) 3959 goto out; 3960 3961 break; 3962 3963 case SND_SOC_DAPM_POST_PMU: 3964 snd_soc_dapm_widget_for_each_sink_path(w, path) { 3965 sink = path->sink->priv; 3966 3967 ret = snd_soc_dai_digital_mute(sink, 0, 3968 SNDRV_PCM_STREAM_PLAYBACK); 3969 if (ret != 0 && ret != -ENOTSUPP) 3970 dev_warn(sink->dev, 3971 "ASoC: Failed to unmute: %d\n", ret); 3972 ret = 0; 3973 } 3974 break; 3975 3976 case SND_SOC_DAPM_PRE_PMD: 3977 snd_soc_dapm_widget_for_each_sink_path(w, path) { 3978 sink = path->sink->priv; 3979 3980 ret = snd_soc_dai_digital_mute(sink, 1, 3981 SNDRV_PCM_STREAM_PLAYBACK); 3982 if (ret != 0 && ret != -ENOTSUPP) 3983 dev_warn(sink->dev, 3984 "ASoC: Failed to mute: %d\n", ret); 3985 ret = 0; 3986 } 3987 3988 substream->stream = SNDRV_PCM_STREAM_CAPTURE; 3989 snd_soc_dapm_widget_for_each_source_path(w, path) { 3990 source = path->source->priv; 3991 snd_soc_dai_hw_free(source, substream); 3992 } 3993 3994 substream->stream = SNDRV_PCM_STREAM_PLAYBACK; 3995 snd_soc_dapm_widget_for_each_sink_path(w, path) { 3996 sink = path->sink->priv; 3997 snd_soc_dai_hw_free(sink, substream); 3998 } 3999 4000 substream->stream = SNDRV_PCM_STREAM_CAPTURE; 4001 snd_soc_dapm_widget_for_each_source_path(w, path) { 4002 source = path->source->priv; 4003 snd_soc_dai_deactivate(source, substream->stream); 4004 snd_soc_dai_shutdown(source, substream, 0); 4005 } 4006 4007 substream->stream = SNDRV_PCM_STREAM_PLAYBACK; 4008 snd_soc_dapm_widget_for_each_sink_path(w, path) { 4009 sink = path->sink->priv; 4010 snd_soc_dai_deactivate(sink, substream->stream); 4011 snd_soc_dai_shutdown(sink, substream, 0); 4012 } 4013 break; 4014 4015 case SND_SOC_DAPM_POST_PMD: 4016 kfree(substream->runtime); 4017 substream->runtime = NULL; 4018 break; 4019 4020 default: 4021 WARN(1, "Unknown event %d\n", event); 4022 ret = -EINVAL; 4023 } 4024 4025out: 4026 /* Restore the substream direction */ 4027 substream->stream = saved_stream; 4028 return ret; 4029} 4030 4031static int snd_soc_dapm_dai_link_get(struct snd_kcontrol *kcontrol, 4032 struct snd_ctl_elem_value *ucontrol) 4033{ 4034 struct snd_soc_dapm_widget *w = snd_kcontrol_chip(kcontrol); 4035 struct snd_soc_pcm_runtime *rtd = w->priv; 4036 4037 ucontrol->value.enumerated.item[0] = rtd->params_select; 4038 4039 return 0; 4040} 4041 4042static int snd_soc_dapm_dai_link_put(struct snd_kcontrol *kcontrol, 4043 struct snd_ctl_elem_value *ucontrol) 4044{ 4045 struct snd_soc_dapm_widget *w = snd_kcontrol_chip(kcontrol); 4046 struct snd_soc_pcm_runtime *rtd = w->priv; 4047 4048 /* Can't change the config when widget is already powered */ 4049 if (w->power) 4050 return -EBUSY; 4051 4052 if (ucontrol->value.enumerated.item[0] == rtd->params_select) 4053 return 0; 4054 4055 if (ucontrol->value.enumerated.item[0] >= rtd->dai_link->num_params) 4056 return -EINVAL; 4057 4058 rtd->params_select = ucontrol->value.enumerated.item[0]; 4059 4060 return 1; 4061} 4062 4063static void 4064snd_soc_dapm_free_kcontrol(struct snd_soc_card *card, 4065 unsigned long *private_value, 4066 int num_params, 4067 const char **w_param_text) 4068{ 4069 int count; 4070 4071 devm_kfree(card->dev, (void *)*private_value); 4072 4073 if (!w_param_text) 4074 return; 4075 4076 for (count = 0 ; count < num_params; count++) 4077 devm_kfree(card->dev, (void *)w_param_text[count]); 4078 devm_kfree(card->dev, w_param_text); 4079} 4080 4081static struct snd_kcontrol_new * 4082snd_soc_dapm_alloc_kcontrol(struct snd_soc_card *card, 4083 char *link_name, 4084 const struct snd_soc_pcm_stream *params, 4085 int num_params, const char **w_param_text, 4086 unsigned long *private_value) 4087{ 4088 struct soc_enum w_param_enum[] = { 4089 SOC_ENUM_SINGLE(0, 0, 0, NULL), 4090 }; 4091 struct snd_kcontrol_new kcontrol_dai_link[] = { 4092 SOC_ENUM_EXT(NULL, w_param_enum[0], 4093 snd_soc_dapm_dai_link_get, 4094 snd_soc_dapm_dai_link_put), 4095 }; 4096 struct snd_kcontrol_new *kcontrol_news; 4097 const struct snd_soc_pcm_stream *config = params; 4098 int count; 4099 4100 for (count = 0 ; count < num_params; count++) { 4101 if (!config->stream_name) { 4102 dev_warn(card->dapm.dev, 4103 "ASoC: anonymous config %d for dai link %s\n", 4104 count, link_name); 4105 w_param_text[count] = 4106 devm_kasprintf(card->dev, GFP_KERNEL, 4107 "Anonymous Configuration %d", 4108 count); 4109 } else { 4110 w_param_text[count] = devm_kmemdup(card->dev, 4111 config->stream_name, 4112 strlen(config->stream_name) + 1, 4113 GFP_KERNEL); 4114 } 4115 if (!w_param_text[count]) 4116 goto outfree_w_param; 4117 config++; 4118 } 4119 4120 w_param_enum[0].items = num_params; 4121 w_param_enum[0].texts = w_param_text; 4122 4123 *private_value = 4124 (unsigned long) devm_kmemdup(card->dev, 4125 (void *)(kcontrol_dai_link[0].private_value), 4126 sizeof(struct soc_enum), GFP_KERNEL); 4127 if (!*private_value) { 4128 dev_err(card->dev, "ASoC: Failed to create control for %s widget\n", 4129 link_name); 4130 goto outfree_w_param; 4131 } 4132 kcontrol_dai_link[0].private_value = *private_value; 4133 /* duplicate kcontrol_dai_link on heap so that memory persists */ 4134 kcontrol_news = devm_kmemdup(card->dev, &kcontrol_dai_link[0], 4135 sizeof(struct snd_kcontrol_new), 4136 GFP_KERNEL); 4137 if (!kcontrol_news) { 4138 dev_err(card->dev, "ASoC: Failed to create control for %s widget\n", 4139 link_name); 4140 goto outfree_w_param; 4141 } 4142 return kcontrol_news; 4143 4144outfree_w_param: 4145 snd_soc_dapm_free_kcontrol(card, private_value, num_params, w_param_text); 4146 return NULL; 4147} 4148 4149static struct snd_soc_dapm_widget * 4150snd_soc_dapm_new_dai(struct snd_soc_card *card, 4151 struct snd_pcm_substream *substream, 4152 char *id) 4153{ 4154 struct snd_soc_pcm_runtime *rtd = asoc_substream_to_rtd(substream); 4155 struct snd_soc_dapm_widget template; 4156 struct snd_soc_dapm_widget *w; 4157 const char **w_param_text; 4158 unsigned long private_value = 0; 4159 char *link_name; 4160 int ret; 4161 4162 link_name = devm_kasprintf(card->dev, GFP_KERNEL, "%s-%s", 4163 rtd->dai_link->name, id); 4164 if (!link_name) 4165 return ERR_PTR(-ENOMEM); 4166 4167 memset(&template, 0, sizeof(template)); 4168 template.reg = SND_SOC_NOPM; 4169 template.id = snd_soc_dapm_dai_link; 4170 template.name = link_name; 4171 template.event = snd_soc_dai_link_event; 4172 template.event_flags = SND_SOC_DAPM_PRE_PMU | SND_SOC_DAPM_POST_PMU | 4173 SND_SOC_DAPM_PRE_PMD | SND_SOC_DAPM_POST_PMD; 4174 template.kcontrol_news = NULL; 4175 4176 /* allocate memory for control, only in case of multiple configs */ 4177 if (rtd->dai_link->num_params > 1) { 4178 w_param_text = devm_kcalloc(card->dev, 4179 rtd->dai_link->num_params, 4180 sizeof(char *), GFP_KERNEL); 4181 if (!w_param_text) { 4182 ret = -ENOMEM; 4183 goto param_fail; 4184 } 4185 4186 template.num_kcontrols = 1; 4187 template.kcontrol_news = 4188 snd_soc_dapm_alloc_kcontrol(card, 4189 link_name, 4190 rtd->dai_link->params, 4191 rtd->dai_link->num_params, 4192 w_param_text, &private_value); 4193 if (!template.kcontrol_news) { 4194 ret = -ENOMEM; 4195 goto param_fail; 4196 } 4197 } else { 4198 w_param_text = NULL; 4199 } 4200 dev_dbg(card->dev, "ASoC: adding %s widget\n", link_name); 4201 4202 w = snd_soc_dapm_new_control_unlocked(&card->dapm, &template); 4203 if (IS_ERR(w)) { 4204 ret = PTR_ERR(w); 4205 dev_err(rtd->dev, "ASoC: Failed to create %s widget: %d\n", 4206 link_name, ret); 4207 goto outfree_kcontrol_news; 4208 } 4209 4210 w->priv = substream; 4211 4212 return w; 4213 4214outfree_kcontrol_news: 4215 devm_kfree(card->dev, (void *)template.kcontrol_news); 4216 snd_soc_dapm_free_kcontrol(card, &private_value, 4217 rtd->dai_link->num_params, w_param_text); 4218param_fail: 4219 devm_kfree(card->dev, link_name); 4220 return ERR_PTR(ret); 4221} 4222 4223int snd_soc_dapm_new_dai_widgets(struct snd_soc_dapm_context *dapm, 4224 struct snd_soc_dai *dai) 4225{ 4226 struct snd_soc_dapm_widget template; 4227 struct snd_soc_dapm_widget *w; 4228 4229 WARN_ON(dapm->dev != dai->dev); 4230 4231 memset(&template, 0, sizeof(template)); 4232 template.reg = SND_SOC_NOPM; 4233 4234 if (dai->driver->playback.stream_name) { 4235 template.id = snd_soc_dapm_dai_in; 4236 template.name = dai->driver->playback.stream_name; 4237 template.sname = dai->driver->playback.stream_name; 4238 4239 dev_dbg(dai->dev, "ASoC: adding %s widget\n", 4240 template.name); 4241 4242 w = snd_soc_dapm_new_control_unlocked(dapm, &template); 4243 if (IS_ERR(w)) 4244 return PTR_ERR(w); 4245 4246 w->priv = dai; 4247 dai->playback_widget = w; 4248 } 4249 4250 if (dai->driver->capture.stream_name) { 4251 template.id = snd_soc_dapm_dai_out; 4252 template.name = dai->driver->capture.stream_name; 4253 template.sname = dai->driver->capture.stream_name; 4254 4255 dev_dbg(dai->dev, "ASoC: adding %s widget\n", 4256 template.name); 4257 4258 w = snd_soc_dapm_new_control_unlocked(dapm, &template); 4259 if (IS_ERR(w)) 4260 return PTR_ERR(w); 4261 4262 w->priv = dai; 4263 dai->capture_widget = w; 4264 } 4265 4266 return 0; 4267} 4268 4269int snd_soc_dapm_link_dai_widgets(struct snd_soc_card *card) 4270{ 4271 struct snd_soc_dapm_widget *dai_w, *w; 4272 struct snd_soc_dapm_widget *src, *sink; 4273 struct snd_soc_dai *dai; 4274 4275 /* For each DAI widget... */ 4276 for_each_card_widgets(card, dai_w) { 4277 switch (dai_w->id) { 4278 case snd_soc_dapm_dai_in: 4279 case snd_soc_dapm_dai_out: 4280 break; 4281 default: 4282 continue; 4283 } 4284 4285 /* let users know there is no DAI to link */ 4286 if (!dai_w->priv) { 4287 dev_dbg(card->dev, "dai widget %s has no DAI\n", 4288 dai_w->name); 4289 continue; 4290 } 4291 4292 dai = dai_w->priv; 4293 4294 /* ...find all widgets with the same stream and link them */ 4295 for_each_card_widgets(card, w) { 4296 if (w->dapm != dai_w->dapm) 4297 continue; 4298 4299 switch (w->id) { 4300 case snd_soc_dapm_dai_in: 4301 case snd_soc_dapm_dai_out: 4302 continue; 4303 default: 4304 break; 4305 } 4306 4307 if (!w->sname || !strstr(w->sname, dai_w->sname)) 4308 continue; 4309 4310 if (dai_w->id == snd_soc_dapm_dai_in) { 4311 src = dai_w; 4312 sink = w; 4313 } else { 4314 src = w; 4315 sink = dai_w; 4316 } 4317 dev_dbg(dai->dev, "%s -> %s\n", src->name, sink->name); 4318 snd_soc_dapm_add_path(w->dapm, src, sink, NULL, NULL); 4319 } 4320 } 4321 4322 return 0; 4323} 4324 4325static void dapm_connect_dai_routes(struct snd_soc_dapm_context *dapm, 4326 struct snd_soc_dai *src_dai, 4327 struct snd_soc_dapm_widget *src, 4328 struct snd_soc_dapm_widget *dai, 4329 struct snd_soc_dai *sink_dai, 4330 struct snd_soc_dapm_widget *sink) 4331{ 4332 dev_dbg(dapm->dev, "connected DAI link %s:%s -> %s:%s\n", 4333 src_dai->component->name, src->name, 4334 sink_dai->component->name, sink->name); 4335 4336 if (dai) { 4337 snd_soc_dapm_add_path(dapm, src, dai, NULL, NULL); 4338 src = dai; 4339 } 4340 4341 snd_soc_dapm_add_path(dapm, src, sink, NULL, NULL); 4342} 4343 4344static void dapm_connect_dai_pair(struct snd_soc_card *card, 4345 struct snd_soc_pcm_runtime *rtd, 4346 struct snd_soc_dai *codec_dai, 4347 struct snd_soc_dai *cpu_dai) 4348{ 4349 struct snd_soc_dai_link *dai_link = rtd->dai_link; 4350 struct snd_soc_dapm_widget *dai, *codec, *playback_cpu, *capture_cpu; 4351 struct snd_pcm_substream *substream; 4352 struct snd_pcm_str *streams = rtd->pcm->streams; 4353 4354 if (dai_link->params) { 4355 playback_cpu = cpu_dai->capture_widget; 4356 capture_cpu = cpu_dai->playback_widget; 4357 } else { 4358 playback_cpu = cpu_dai->playback_widget; 4359 capture_cpu = cpu_dai->capture_widget; 4360 } 4361 4362 /* connect BE DAI playback if widgets are valid */ 4363 codec = codec_dai->playback_widget; 4364 4365 if (playback_cpu && codec) { 4366 if (dai_link->params && !rtd->playback_widget) { 4367 substream = streams[SNDRV_PCM_STREAM_PLAYBACK].substream; 4368 dai = snd_soc_dapm_new_dai(card, substream, "playback"); 4369 if (IS_ERR(dai)) 4370 goto capture; 4371 rtd->playback_widget = dai; 4372 } 4373 4374 dapm_connect_dai_routes(&card->dapm, cpu_dai, playback_cpu, 4375 rtd->playback_widget, 4376 codec_dai, codec); 4377 } 4378 4379capture: 4380 /* connect BE DAI capture if widgets are valid */ 4381 codec = codec_dai->capture_widget; 4382 4383 if (codec && capture_cpu) { 4384 if (dai_link->params && !rtd->capture_widget) { 4385 substream = streams[SNDRV_PCM_STREAM_CAPTURE].substream; 4386 dai = snd_soc_dapm_new_dai(card, substream, "capture"); 4387 if (IS_ERR(dai)) 4388 return; 4389 rtd->capture_widget = dai; 4390 } 4391 4392 dapm_connect_dai_routes(&card->dapm, codec_dai, codec, 4393 rtd->capture_widget, 4394 cpu_dai, capture_cpu); 4395 } 4396} 4397 4398static void soc_dapm_dai_stream_event(struct snd_soc_dai *dai, int stream, 4399 int event) 4400{ 4401 struct snd_soc_dapm_widget *w; 4402 unsigned int ep; 4403 4404 w = snd_soc_dai_get_widget(dai, stream); 4405 4406 if (w) { 4407 dapm_mark_dirty(w, "stream event"); 4408 4409 if (w->id == snd_soc_dapm_dai_in) { 4410 ep = SND_SOC_DAPM_EP_SOURCE; 4411 dapm_widget_invalidate_input_paths(w); 4412 } else { 4413 ep = SND_SOC_DAPM_EP_SINK; 4414 dapm_widget_invalidate_output_paths(w); 4415 } 4416 4417 switch (event) { 4418 case SND_SOC_DAPM_STREAM_START: 4419 w->active = 1; 4420 w->is_ep = ep; 4421 break; 4422 case SND_SOC_DAPM_STREAM_STOP: 4423 w->active = 0; 4424 w->is_ep = 0; 4425 break; 4426 case SND_SOC_DAPM_STREAM_SUSPEND: 4427 case SND_SOC_DAPM_STREAM_RESUME: 4428 case SND_SOC_DAPM_STREAM_PAUSE_PUSH: 4429 case SND_SOC_DAPM_STREAM_PAUSE_RELEASE: 4430 break; 4431 } 4432 } 4433} 4434 4435void snd_soc_dapm_connect_dai_link_widgets(struct snd_soc_card *card) 4436{ 4437 struct snd_soc_pcm_runtime *rtd; 4438 struct snd_soc_dai *codec_dai; 4439 int i; 4440 4441 /* for each BE DAI link... */ 4442 for_each_card_rtds(card, rtd) { 4443 /* 4444 * dynamic FE links have no fixed DAI mapping. 4445 * CODEC<->CODEC links have no direct connection. 4446 */ 4447 if (rtd->dai_link->dynamic) 4448 continue; 4449 4450 if (rtd->num_cpus == 1) { 4451 for_each_rtd_codec_dais(rtd, i, codec_dai) 4452 dapm_connect_dai_pair(card, rtd, codec_dai, 4453 asoc_rtd_to_cpu(rtd, 0)); 4454 } else if (rtd->num_codecs == rtd->num_cpus) { 4455 for_each_rtd_codec_dais(rtd, i, codec_dai) 4456 dapm_connect_dai_pair(card, rtd, codec_dai, 4457 asoc_rtd_to_cpu(rtd, i)); 4458 } else { 4459 dev_err(card->dev, 4460 "N cpus to M codecs link is not supported yet\n"); 4461 } 4462 } 4463} 4464 4465static void soc_dapm_stream_event(struct snd_soc_pcm_runtime *rtd, int stream, 4466 int event) 4467{ 4468 struct snd_soc_dai *dai; 4469 int i; 4470 4471 for_each_rtd_dais(rtd, i, dai) 4472 soc_dapm_dai_stream_event(dai, stream, event); 4473 4474 dapm_power_widgets(rtd->card, event); 4475} 4476 4477/** 4478 * snd_soc_dapm_stream_event - send a stream event to the dapm core 4479 * @rtd: PCM runtime data 4480 * @stream: stream name 4481 * @event: stream event 4482 * 4483 * Sends a stream event to the dapm core. The core then makes any 4484 * necessary widget power changes. 4485 * 4486 * Returns 0 for success else error. 4487 */ 4488void snd_soc_dapm_stream_event(struct snd_soc_pcm_runtime *rtd, int stream, 4489 int event) 4490{ 4491 struct snd_soc_card *card = rtd->card; 4492 4493 mutex_lock_nested(&card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 4494 soc_dapm_stream_event(rtd, stream, event); 4495 mutex_unlock(&card->dapm_mutex); 4496} 4497 4498void snd_soc_dapm_stream_stop(struct snd_soc_pcm_runtime *rtd, int stream) 4499{ 4500 if (stream == SNDRV_PCM_STREAM_PLAYBACK) { 4501 if (snd_soc_runtime_ignore_pmdown_time(rtd)) { 4502 /* powered down playback stream now */ 4503 snd_soc_dapm_stream_event(rtd, 4504 SNDRV_PCM_STREAM_PLAYBACK, 4505 SND_SOC_DAPM_STREAM_STOP); 4506 } else { 4507 /* start delayed pop wq here for playback streams */ 4508 rtd->pop_wait = 1; 4509 queue_delayed_work(system_power_efficient_wq, 4510 &rtd->delayed_work, 4511 msecs_to_jiffies(rtd->pmdown_time)); 4512 } 4513 } else { 4514 /* capture streams can be powered down now */ 4515 snd_soc_dapm_stream_event(rtd, SNDRV_PCM_STREAM_CAPTURE, 4516 SND_SOC_DAPM_STREAM_STOP); 4517 } 4518} 4519EXPORT_SYMBOL_GPL(snd_soc_dapm_stream_stop); 4520 4521/** 4522 * snd_soc_dapm_enable_pin_unlocked - enable pin. 4523 * @dapm: DAPM context 4524 * @pin: pin name 4525 * 4526 * Enables input/output pin and its parents or children widgets iff there is 4527 * a valid audio route and active audio stream. 4528 * 4529 * Requires external locking. 4530 * 4531 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 4532 * do any widget power switching. 4533 */ 4534int snd_soc_dapm_enable_pin_unlocked(struct snd_soc_dapm_context *dapm, 4535 const char *pin) 4536{ 4537 return snd_soc_dapm_set_pin(dapm, pin, 1); 4538} 4539EXPORT_SYMBOL_GPL(snd_soc_dapm_enable_pin_unlocked); 4540 4541/** 4542 * snd_soc_dapm_enable_pin - enable pin. 4543 * @dapm: DAPM context 4544 * @pin: pin name 4545 * 4546 * Enables input/output pin and its parents or children widgets iff there is 4547 * a valid audio route and active audio stream. 4548 * 4549 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 4550 * do any widget power switching. 4551 */ 4552int snd_soc_dapm_enable_pin(struct snd_soc_dapm_context *dapm, const char *pin) 4553{ 4554 int ret; 4555 4556 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 4557 4558 ret = snd_soc_dapm_set_pin(dapm, pin, 1); 4559 4560 mutex_unlock(&dapm->card->dapm_mutex); 4561 4562 return ret; 4563} 4564EXPORT_SYMBOL_GPL(snd_soc_dapm_enable_pin); 4565 4566/** 4567 * snd_soc_dapm_force_enable_pin_unlocked - force a pin to be enabled 4568 * @dapm: DAPM context 4569 * @pin: pin name 4570 * 4571 * Enables input/output pin regardless of any other state. This is 4572 * intended for use with microphone bias supplies used in microphone 4573 * jack detection. 4574 * 4575 * Requires external locking. 4576 * 4577 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 4578 * do any widget power switching. 4579 */ 4580int snd_soc_dapm_force_enable_pin_unlocked(struct snd_soc_dapm_context *dapm, 4581 const char *pin) 4582{ 4583 struct snd_soc_dapm_widget *w = dapm_find_widget(dapm, pin, true); 4584 4585 if (!w) { 4586 dev_err(dapm->dev, "ASoC: unknown pin %s\n", pin); 4587 return -EINVAL; 4588 } 4589 4590 dev_dbg(w->dapm->dev, "ASoC: force enable pin %s\n", pin); 4591 if (!w->connected) { 4592 /* 4593 * w->force does not affect the number of input or output paths, 4594 * so we only have to recheck if w->connected is changed 4595 */ 4596 dapm_widget_invalidate_input_paths(w); 4597 dapm_widget_invalidate_output_paths(w); 4598 w->connected = 1; 4599 } 4600 w->force = 1; 4601 dapm_mark_dirty(w, "force enable"); 4602 4603 return 0; 4604} 4605EXPORT_SYMBOL_GPL(snd_soc_dapm_force_enable_pin_unlocked); 4606 4607/** 4608 * snd_soc_dapm_force_enable_pin - force a pin to be enabled 4609 * @dapm: DAPM context 4610 * @pin: pin name 4611 * 4612 * Enables input/output pin regardless of any other state. This is 4613 * intended for use with microphone bias supplies used in microphone 4614 * jack detection. 4615 * 4616 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 4617 * do any widget power switching. 4618 */ 4619int snd_soc_dapm_force_enable_pin(struct snd_soc_dapm_context *dapm, 4620 const char *pin) 4621{ 4622 int ret; 4623 4624 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 4625 4626 ret = snd_soc_dapm_force_enable_pin_unlocked(dapm, pin); 4627 4628 mutex_unlock(&dapm->card->dapm_mutex); 4629 4630 return ret; 4631} 4632EXPORT_SYMBOL_GPL(snd_soc_dapm_force_enable_pin); 4633 4634/** 4635 * snd_soc_dapm_disable_pin_unlocked - disable pin. 4636 * @dapm: DAPM context 4637 * @pin: pin name 4638 * 4639 * Disables input/output pin and its parents or children widgets. 4640 * 4641 * Requires external locking. 4642 * 4643 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 4644 * do any widget power switching. 4645 */ 4646int snd_soc_dapm_disable_pin_unlocked(struct snd_soc_dapm_context *dapm, 4647 const char *pin) 4648{ 4649 return snd_soc_dapm_set_pin(dapm, pin, 0); 4650} 4651EXPORT_SYMBOL_GPL(snd_soc_dapm_disable_pin_unlocked); 4652 4653/** 4654 * snd_soc_dapm_disable_pin - disable pin. 4655 * @dapm: DAPM context 4656 * @pin: pin name 4657 * 4658 * Disables input/output pin and its parents or children widgets. 4659 * 4660 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 4661 * do any widget power switching. 4662 */ 4663int snd_soc_dapm_disable_pin(struct snd_soc_dapm_context *dapm, 4664 const char *pin) 4665{ 4666 int ret; 4667 4668 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 4669 4670 ret = snd_soc_dapm_set_pin(dapm, pin, 0); 4671 4672 mutex_unlock(&dapm->card->dapm_mutex); 4673 4674 return ret; 4675} 4676EXPORT_SYMBOL_GPL(snd_soc_dapm_disable_pin); 4677 4678/** 4679 * snd_soc_dapm_nc_pin_unlocked - permanently disable pin. 4680 * @dapm: DAPM context 4681 * @pin: pin name 4682 * 4683 * Marks the specified pin as being not connected, disabling it along 4684 * any parent or child widgets. At present this is identical to 4685 * snd_soc_dapm_disable_pin() but in future it will be extended to do 4686 * additional things such as disabling controls which only affect 4687 * paths through the pin. 4688 * 4689 * Requires external locking. 4690 * 4691 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 4692 * do any widget power switching. 4693 */ 4694int snd_soc_dapm_nc_pin_unlocked(struct snd_soc_dapm_context *dapm, 4695 const char *pin) 4696{ 4697 return snd_soc_dapm_set_pin(dapm, pin, 0); 4698} 4699EXPORT_SYMBOL_GPL(snd_soc_dapm_nc_pin_unlocked); 4700 4701/** 4702 * snd_soc_dapm_nc_pin - permanently disable pin. 4703 * @dapm: DAPM context 4704 * @pin: pin name 4705 * 4706 * Marks the specified pin as being not connected, disabling it along 4707 * any parent or child widgets. At present this is identical to 4708 * snd_soc_dapm_disable_pin() but in future it will be extended to do 4709 * additional things such as disabling controls which only affect 4710 * paths through the pin. 4711 * 4712 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 4713 * do any widget power switching. 4714 */ 4715int snd_soc_dapm_nc_pin(struct snd_soc_dapm_context *dapm, const char *pin) 4716{ 4717 int ret; 4718 4719 mutex_lock_nested(&dapm->card->dapm_mutex, SND_SOC_DAPM_CLASS_RUNTIME); 4720 4721 ret = snd_soc_dapm_set_pin(dapm, pin, 0); 4722 4723 mutex_unlock(&dapm->card->dapm_mutex); 4724 4725 return ret; 4726} 4727EXPORT_SYMBOL_GPL(snd_soc_dapm_nc_pin); 4728 4729/** 4730 * snd_soc_dapm_get_pin_status - get audio pin status 4731 * @dapm: DAPM context 4732 * @pin: audio signal pin endpoint (or start point) 4733 * 4734 * Get audio pin status - connected or disconnected. 4735 * 4736 * Returns 1 for connected otherwise 0. 4737 */ 4738int snd_soc_dapm_get_pin_status(struct snd_soc_dapm_context *dapm, 4739 const char *pin) 4740{ 4741 struct snd_soc_dapm_widget *w = dapm_find_widget(dapm, pin, true); 4742 4743 if (w) 4744 return w->connected; 4745 4746 return 0; 4747} 4748EXPORT_SYMBOL_GPL(snd_soc_dapm_get_pin_status); 4749 4750/** 4751 * snd_soc_dapm_ignore_suspend - ignore suspend status for DAPM endpoint 4752 * @dapm: DAPM context 4753 * @pin: audio signal pin endpoint (or start point) 4754 * 4755 * Mark the given endpoint or pin as ignoring suspend. When the 4756 * system is disabled a path between two endpoints flagged as ignoring 4757 * suspend will not be disabled. The path must already be enabled via 4758 * normal means at suspend time, it will not be turned on if it was not 4759 * already enabled. 4760 */ 4761int snd_soc_dapm_ignore_suspend(struct snd_soc_dapm_context *dapm, 4762 const char *pin) 4763{ 4764 struct snd_soc_dapm_widget *w = dapm_find_widget(dapm, pin, false); 4765 4766 if (!w) { 4767 dev_err(dapm->dev, "ASoC: unknown pin %s\n", pin); 4768 return -EINVAL; 4769 } 4770 4771 w->ignore_suspend = 1; 4772 4773 return 0; 4774} 4775EXPORT_SYMBOL_GPL(snd_soc_dapm_ignore_suspend); 4776 4777/** 4778 * snd_soc_dapm_free - free dapm resources 4779 * @dapm: DAPM context 4780 * 4781 * Free all dapm widgets and resources. 4782 */ 4783void snd_soc_dapm_free(struct snd_soc_dapm_context *dapm) 4784{ 4785 dapm_debugfs_cleanup(dapm); 4786 dapm_free_widgets(dapm); 4787 list_del(&dapm->list); 4788} 4789EXPORT_SYMBOL_GPL(snd_soc_dapm_free); 4790 4791void snd_soc_dapm_init(struct snd_soc_dapm_context *dapm, 4792 struct snd_soc_card *card, 4793 struct snd_soc_component *component) 4794{ 4795 dapm->card = card; 4796 dapm->component = component; 4797 dapm->bias_level = SND_SOC_BIAS_OFF; 4798 4799 if (component) { 4800 dapm->dev = component->dev; 4801 dapm->idle_bias_off = !component->driver->idle_bias_on, 4802 dapm->suspend_bias_off = component->driver->suspend_bias_off; 4803 } else { 4804 dapm->dev = card->dev; 4805 } 4806 4807 INIT_LIST_HEAD(&dapm->list); 4808 /* see for_each_card_dapms */ 4809 list_add(&dapm->list, &card->dapm_list); 4810} 4811EXPORT_SYMBOL_GPL(snd_soc_dapm_init); 4812 4813static void soc_dapm_shutdown_dapm(struct snd_soc_dapm_context *dapm) 4814{ 4815 struct snd_soc_card *card = dapm->card; 4816 struct snd_soc_dapm_widget *w; 4817 LIST_HEAD(down_list); 4818 int powerdown = 0; 4819 4820 mutex_lock(&card->dapm_mutex); 4821 4822 for_each_card_widgets(dapm->card, w) { 4823 if (w->dapm != dapm) 4824 continue; 4825 if (w->power) { 4826 dapm_seq_insert(w, &down_list, false); 4827 w->new_power = 0; 4828 powerdown = 1; 4829 } 4830 } 4831 4832 /* If there were no widgets to power down we're already in 4833 * standby. 4834 */ 4835 if (powerdown) { 4836 if (dapm->bias_level == SND_SOC_BIAS_ON) 4837 snd_soc_dapm_set_bias_level(dapm, 4838 SND_SOC_BIAS_PREPARE); 4839 dapm_seq_run(card, &down_list, 0, false); 4840 if (dapm->bias_level == SND_SOC_BIAS_PREPARE) 4841 snd_soc_dapm_set_bias_level(dapm, 4842 SND_SOC_BIAS_STANDBY); 4843 } 4844 4845 mutex_unlock(&card->dapm_mutex); 4846} 4847 4848/* 4849 * snd_soc_dapm_shutdown - callback for system shutdown 4850 */ 4851void snd_soc_dapm_shutdown(struct snd_soc_card *card) 4852{ 4853 struct snd_soc_dapm_context *dapm; 4854 4855 for_each_card_dapms(card, dapm) { 4856 if (dapm != &card->dapm) { 4857 soc_dapm_shutdown_dapm(dapm); 4858 if (dapm->bias_level == SND_SOC_BIAS_STANDBY) 4859 snd_soc_dapm_set_bias_level(dapm, 4860 SND_SOC_BIAS_OFF); 4861 } 4862 } 4863 4864 soc_dapm_shutdown_dapm(&card->dapm); 4865 if (card->dapm.bias_level == SND_SOC_BIAS_STANDBY) 4866 snd_soc_dapm_set_bias_level(&card->dapm, 4867 SND_SOC_BIAS_OFF); 4868} 4869 4870/* Module information */ 4871MODULE_AUTHOR("Liam Girdwood, lrg@slimlogic.co.uk"); 4872MODULE_DESCRIPTION("Dynamic Audio Power Management core for ALSA SoC"); 4873MODULE_LICENSE("GPL"); 4874