1 /* 2 * soc-dapm.c -- ALSA SoC Dynamic Audio Power Management 3 * 4 * Copyright 2005 Wolfson Microelectronics PLC. 5 * Author: Liam Girdwood <lrg@slimlogic.co.uk> 6 * 7 * This program is free software; you can redistribute it and/or modify it 8 * under the terms of the GNU General Public License as published by the 9 * Free Software Foundation; either version 2 of the License, or (at your 10 * option) any later version. 11 * 12 * Features: 13 * o Changes power status of internal codec blocks depending on the 14 * dynamic configuration of codec internal audio paths and active 15 * DACs/ADCs. 16 * o Platform power domain - can support external components i.e. amps and 17 * mic/meadphone insertion events. 18 * o Automatic Mic Bias support 19 * o Jack insertion power event initiation - e.g. hp insertion will enable 20 * sinks, dacs, etc 21 * o Delayed powerdown of audio susbsystem to reduce pops between a quick 22 * device reopen. 23 * 24 * Todo: 25 * o DAPM power change sequencing - allow for configurable per 26 * codec sequences. 27 * o Support for analogue bias optimisation. 28 * o Support for reduced codec oversampling rates. 29 * o Support for reduced codec bias currents. 30 */ 31 32 #include <linux/module.h> 33 #include <linux/moduleparam.h> 34 #include <linux/init.h> 35 #include <linux/async.h> 36 #include <linux/delay.h> 37 #include <linux/pm.h> 38 #include <linux/bitops.h> 39 #include <linux/platform_device.h> 40 #include <linux/jiffies.h> 41 #include <linux/debugfs.h> 42 #include <linux/slab.h> 43 #include <sound/core.h> 44 #include <sound/pcm.h> 45 #include <sound/pcm_params.h> 46 #include <sound/soc.h> 47 #include <sound/initval.h> 48 49 #include <trace/events/asoc.h> 50 51 /* dapm power sequences - make this per codec in the future */ 52 static int dapm_up_seq[] = { 53 [snd_soc_dapm_pre] = 0, 54 [snd_soc_dapm_supply] = 1, 55 [snd_soc_dapm_micbias] = 2, 56 [snd_soc_dapm_aif_in] = 3, 57 [snd_soc_dapm_aif_out] = 3, 58 [snd_soc_dapm_mic] = 4, 59 [snd_soc_dapm_mux] = 5, 60 [snd_soc_dapm_virt_mux] = 5, 61 [snd_soc_dapm_value_mux] = 5, 62 [snd_soc_dapm_dac] = 6, 63 [snd_soc_dapm_mixer] = 7, 64 [snd_soc_dapm_mixer_named_ctl] = 7, 65 [snd_soc_dapm_pga] = 8, 66 [snd_soc_dapm_adc] = 9, 67 [snd_soc_dapm_out_drv] = 10, 68 [snd_soc_dapm_hp] = 10, 69 [snd_soc_dapm_spk] = 10, 70 [snd_soc_dapm_post] = 11, 71 }; 72 73 static int dapm_down_seq[] = { 74 [snd_soc_dapm_pre] = 0, 75 [snd_soc_dapm_adc] = 1, 76 [snd_soc_dapm_hp] = 2, 77 [snd_soc_dapm_spk] = 2, 78 [snd_soc_dapm_out_drv] = 2, 79 [snd_soc_dapm_pga] = 4, 80 [snd_soc_dapm_mixer_named_ctl] = 5, 81 [snd_soc_dapm_mixer] = 5, 82 [snd_soc_dapm_dac] = 6, 83 [snd_soc_dapm_mic] = 7, 84 [snd_soc_dapm_micbias] = 8, 85 [snd_soc_dapm_mux] = 9, 86 [snd_soc_dapm_virt_mux] = 9, 87 [snd_soc_dapm_value_mux] = 9, 88 [snd_soc_dapm_aif_in] = 10, 89 [snd_soc_dapm_aif_out] = 10, 90 [snd_soc_dapm_supply] = 11, 91 [snd_soc_dapm_post] = 12, 92 }; 93 94 static void pop_wait(u32 pop_time) 95 { 96 if (pop_time) 97 schedule_timeout_uninterruptible(msecs_to_jiffies(pop_time)); 98 } 99 100 static void pop_dbg(struct device *dev, u32 pop_time, const char *fmt, ...) 101 { 102 va_list args; 103 char *buf; 104 105 if (!pop_time) 106 return; 107 108 buf = kmalloc(PAGE_SIZE, GFP_KERNEL); 109 if (buf == NULL) 110 return; 111 112 va_start(args, fmt); 113 vsnprintf(buf, PAGE_SIZE, fmt, args); 114 dev_info(dev, "%s", buf); 115 va_end(args); 116 117 kfree(buf); 118 } 119 120 /* create a new dapm widget */ 121 static inline struct snd_soc_dapm_widget *dapm_cnew_widget( 122 const struct snd_soc_dapm_widget *_widget) 123 { 124 return kmemdup(_widget, sizeof(*_widget), GFP_KERNEL); 125 } 126 127 /* get snd_card from DAPM context */ 128 static inline struct snd_card *dapm_get_snd_card( 129 struct snd_soc_dapm_context *dapm) 130 { 131 if (dapm->codec) 132 return dapm->codec->card->snd_card; 133 else if (dapm->platform) 134 return dapm->platform->card->snd_card; 135 else 136 BUG(); 137 138 /* unreachable */ 139 return NULL; 140 } 141 142 /* get soc_card from DAPM context */ 143 static inline struct snd_soc_card *dapm_get_soc_card( 144 struct snd_soc_dapm_context *dapm) 145 { 146 if (dapm->codec) 147 return dapm->codec->card; 148 else if (dapm->platform) 149 return dapm->platform->card; 150 else 151 BUG(); 152 153 /* unreachable */ 154 return NULL; 155 } 156 157 static int soc_widget_read(struct snd_soc_dapm_widget *w, int reg) 158 { 159 if (w->codec) 160 return snd_soc_read(w->codec, reg); 161 else if (w->platform) 162 return snd_soc_platform_read(w->platform, reg); 163 164 dev_err(w->dapm->dev, "no valid widget read method\n"); 165 return -1; 166 } 167 168 static int soc_widget_write(struct snd_soc_dapm_widget *w, int reg, int val) 169 { 170 if (w->codec) 171 return snd_soc_write(w->codec, reg, val); 172 else if (w->platform) 173 return snd_soc_platform_write(w->platform, reg, val); 174 175 dev_err(w->dapm->dev, "no valid widget write method\n"); 176 return -1; 177 } 178 179 static int soc_widget_update_bits(struct snd_soc_dapm_widget *w, 180 unsigned short reg, unsigned int mask, unsigned int value) 181 { 182 int change; 183 unsigned int old, new; 184 int ret; 185 186 ret = soc_widget_read(w, reg); 187 if (ret < 0) 188 return ret; 189 190 old = ret; 191 new = (old & ~mask) | (value & mask); 192 change = old != new; 193 if (change) { 194 ret = soc_widget_write(w, reg, new); 195 if (ret < 0) 196 return ret; 197 } 198 199 return change; 200 } 201 202 /** 203 * snd_soc_dapm_set_bias_level - set the bias level for the system 204 * @dapm: DAPM context 205 * @level: level to configure 206 * 207 * Configure the bias (power) levels for the SoC audio device. 208 * 209 * Returns 0 for success else error. 210 */ 211 static int snd_soc_dapm_set_bias_level(struct snd_soc_dapm_context *dapm, 212 enum snd_soc_bias_level level) 213 { 214 struct snd_soc_card *card = dapm->card; 215 int ret = 0; 216 217 trace_snd_soc_bias_level_start(card, level); 218 219 if (card && card->set_bias_level) 220 ret = card->set_bias_level(card, dapm, level); 221 if (ret != 0) 222 goto out; 223 224 if (dapm->codec) { 225 if (dapm->codec->driver->set_bias_level) 226 ret = dapm->codec->driver->set_bias_level(dapm->codec, 227 level); 228 else 229 dapm->bias_level = level; 230 } 231 if (ret != 0) 232 goto out; 233 234 if (card && card->set_bias_level_post) 235 ret = card->set_bias_level_post(card, dapm, level); 236 out: 237 trace_snd_soc_bias_level_done(card, level); 238 239 return ret; 240 } 241 242 /* set up initial codec paths */ 243 static void dapm_set_path_status(struct snd_soc_dapm_widget *w, 244 struct snd_soc_dapm_path *p, int i) 245 { 246 switch (w->id) { 247 case snd_soc_dapm_switch: 248 case snd_soc_dapm_mixer: 249 case snd_soc_dapm_mixer_named_ctl: { 250 int val; 251 struct soc_mixer_control *mc = (struct soc_mixer_control *) 252 w->kcontrol_news[i].private_value; 253 unsigned int reg = mc->reg; 254 unsigned int shift = mc->shift; 255 int max = mc->max; 256 unsigned int mask = (1 << fls(max)) - 1; 257 unsigned int invert = mc->invert; 258 259 val = soc_widget_read(w, reg); 260 val = (val >> shift) & mask; 261 262 if ((invert && !val) || (!invert && val)) 263 p->connect = 1; 264 else 265 p->connect = 0; 266 } 267 break; 268 case snd_soc_dapm_mux: { 269 struct soc_enum *e = (struct soc_enum *) 270 w->kcontrol_news[i].private_value; 271 int val, item, bitmask; 272 273 for (bitmask = 1; bitmask < e->max; bitmask <<= 1) 274 ; 275 val = soc_widget_read(w, e->reg); 276 item = (val >> e->shift_l) & (bitmask - 1); 277 278 p->connect = 0; 279 for (i = 0; i < e->max; i++) { 280 if (!(strcmp(p->name, e->texts[i])) && item == i) 281 p->connect = 1; 282 } 283 } 284 break; 285 case snd_soc_dapm_virt_mux: { 286 struct soc_enum *e = (struct soc_enum *) 287 w->kcontrol_news[i].private_value; 288 289 p->connect = 0; 290 /* since a virtual mux has no backing registers to 291 * decide which path to connect, it will try to match 292 * with the first enumeration. This is to ensure 293 * that the default mux choice (the first) will be 294 * correctly powered up during initialization. 295 */ 296 if (!strcmp(p->name, e->texts[0])) 297 p->connect = 1; 298 } 299 break; 300 case snd_soc_dapm_value_mux: { 301 struct soc_enum *e = (struct soc_enum *) 302 w->kcontrol_news[i].private_value; 303 int val, item; 304 305 val = soc_widget_read(w, e->reg); 306 val = (val >> e->shift_l) & e->mask; 307 for (item = 0; item < e->max; item++) { 308 if (val == e->values[item]) 309 break; 310 } 311 312 p->connect = 0; 313 for (i = 0; i < e->max; i++) { 314 if (!(strcmp(p->name, e->texts[i])) && item == i) 315 p->connect = 1; 316 } 317 } 318 break; 319 /* does not effect routing - always connected */ 320 case snd_soc_dapm_pga: 321 case snd_soc_dapm_out_drv: 322 case snd_soc_dapm_output: 323 case snd_soc_dapm_adc: 324 case snd_soc_dapm_input: 325 case snd_soc_dapm_dac: 326 case snd_soc_dapm_micbias: 327 case snd_soc_dapm_vmid: 328 case snd_soc_dapm_supply: 329 case snd_soc_dapm_aif_in: 330 case snd_soc_dapm_aif_out: 331 p->connect = 1; 332 break; 333 /* does effect routing - dynamically connected */ 334 case snd_soc_dapm_hp: 335 case snd_soc_dapm_mic: 336 case snd_soc_dapm_spk: 337 case snd_soc_dapm_line: 338 case snd_soc_dapm_pre: 339 case snd_soc_dapm_post: 340 p->connect = 0; 341 break; 342 } 343 } 344 345 /* connect mux widget to its interconnecting audio paths */ 346 static int dapm_connect_mux(struct snd_soc_dapm_context *dapm, 347 struct snd_soc_dapm_widget *src, struct snd_soc_dapm_widget *dest, 348 struct snd_soc_dapm_path *path, const char *control_name, 349 const struct snd_kcontrol_new *kcontrol) 350 { 351 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 352 int i; 353 354 for (i = 0; i < e->max; i++) { 355 if (!(strcmp(control_name, e->texts[i]))) { 356 list_add(&path->list, &dapm->card->paths); 357 list_add(&path->list_sink, &dest->sources); 358 list_add(&path->list_source, &src->sinks); 359 path->name = (char*)e->texts[i]; 360 dapm_set_path_status(dest, path, 0); 361 return 0; 362 } 363 } 364 365 return -ENODEV; 366 } 367 368 /* connect mixer widget to its interconnecting audio paths */ 369 static int dapm_connect_mixer(struct snd_soc_dapm_context *dapm, 370 struct snd_soc_dapm_widget *src, struct snd_soc_dapm_widget *dest, 371 struct snd_soc_dapm_path *path, const char *control_name) 372 { 373 int i; 374 375 /* search for mixer kcontrol */ 376 for (i = 0; i < dest->num_kcontrols; i++) { 377 if (!strcmp(control_name, dest->kcontrol_news[i].name)) { 378 list_add(&path->list, &dapm->card->paths); 379 list_add(&path->list_sink, &dest->sources); 380 list_add(&path->list_source, &src->sinks); 381 path->name = dest->kcontrol_news[i].name; 382 dapm_set_path_status(dest, path, i); 383 return 0; 384 } 385 } 386 return -ENODEV; 387 } 388 389 static int dapm_is_shared_kcontrol(struct snd_soc_dapm_context *dapm, 390 struct snd_soc_dapm_widget *kcontrolw, 391 const struct snd_kcontrol_new *kcontrol_new, 392 struct snd_kcontrol **kcontrol) 393 { 394 struct snd_soc_dapm_widget *w; 395 int i; 396 397 *kcontrol = NULL; 398 399 list_for_each_entry(w, &dapm->card->widgets, list) { 400 if (w == kcontrolw || w->dapm != kcontrolw->dapm) 401 continue; 402 for (i = 0; i < w->num_kcontrols; i++) { 403 if (&w->kcontrol_news[i] == kcontrol_new) { 404 if (w->kcontrols) 405 *kcontrol = w->kcontrols[i]; 406 return 1; 407 } 408 } 409 } 410 411 return 0; 412 } 413 414 /* create new dapm mixer control */ 415 static int dapm_new_mixer(struct snd_soc_dapm_widget *w) 416 { 417 struct snd_soc_dapm_context *dapm = w->dapm; 418 int i, ret = 0; 419 size_t name_len, prefix_len; 420 struct snd_soc_dapm_path *path; 421 struct snd_card *card = dapm->card->snd_card; 422 const char *prefix; 423 struct snd_soc_dapm_widget_list *wlist; 424 size_t wlistsize; 425 426 if (dapm->codec) 427 prefix = dapm->codec->name_prefix; 428 else 429 prefix = NULL; 430 431 if (prefix) 432 prefix_len = strlen(prefix) + 1; 433 else 434 prefix_len = 0; 435 436 /* add kcontrol */ 437 for (i = 0; i < w->num_kcontrols; i++) { 438 439 /* match name */ 440 list_for_each_entry(path, &w->sources, list_sink) { 441 442 /* mixer/mux paths name must match control name */ 443 if (path->name != (char *)w->kcontrol_news[i].name) 444 continue; 445 446 wlistsize = sizeof(struct snd_soc_dapm_widget_list) + 447 sizeof(struct snd_soc_dapm_widget *), 448 wlist = kzalloc(wlistsize, GFP_KERNEL); 449 if (wlist == NULL) { 450 dev_err(dapm->dev, 451 "asoc: can't allocate widget list for %s\n", 452 w->name); 453 return -ENOMEM; 454 } 455 wlist->num_widgets = 1; 456 wlist->widgets[0] = w; 457 458 /* add dapm control with long name. 459 * for dapm_mixer this is the concatenation of the 460 * mixer and kcontrol name. 461 * for dapm_mixer_named_ctl this is simply the 462 * kcontrol name. 463 */ 464 name_len = strlen(w->kcontrol_news[i].name) + 1; 465 if (w->id != snd_soc_dapm_mixer_named_ctl) 466 name_len += 1 + strlen(w->name); 467 468 path->long_name = kmalloc(name_len, GFP_KERNEL); 469 470 if (path->long_name == NULL) { 471 kfree(wlist); 472 return -ENOMEM; 473 } 474 475 switch (w->id) { 476 default: 477 /* The control will get a prefix from 478 * the control creation process but 479 * we're also using the same prefix 480 * for widgets so cut the prefix off 481 * the front of the widget name. 482 */ 483 snprintf(path->long_name, name_len, "%s %s", 484 w->name + prefix_len, 485 w->kcontrol_news[i].name); 486 break; 487 case snd_soc_dapm_mixer_named_ctl: 488 snprintf(path->long_name, name_len, "%s", 489 w->kcontrol_news[i].name); 490 break; 491 } 492 493 path->long_name[name_len - 1] = '\0'; 494 495 path->kcontrol = snd_soc_cnew(&w->kcontrol_news[i], 496 wlist, path->long_name, 497 prefix); 498 ret = snd_ctl_add(card, path->kcontrol); 499 if (ret < 0) { 500 dev_err(dapm->dev, 501 "asoc: failed to add dapm kcontrol %s: %d\n", 502 path->long_name, ret); 503 kfree(wlist); 504 kfree(path->long_name); 505 path->long_name = NULL; 506 return ret; 507 } 508 w->kcontrols[i] = path->kcontrol; 509 } 510 } 511 return ret; 512 } 513 514 /* create new dapm mux control */ 515 static int dapm_new_mux(struct snd_soc_dapm_widget *w) 516 { 517 struct snd_soc_dapm_context *dapm = w->dapm; 518 struct snd_soc_dapm_path *path = NULL; 519 struct snd_kcontrol *kcontrol; 520 struct snd_card *card = dapm->card->snd_card; 521 const char *prefix; 522 size_t prefix_len; 523 int ret; 524 struct snd_soc_dapm_widget_list *wlist; 525 int shared, wlistentries; 526 size_t wlistsize; 527 char *name; 528 529 if (w->num_kcontrols != 1) { 530 dev_err(dapm->dev, 531 "asoc: mux %s has incorrect number of controls\n", 532 w->name); 533 return -EINVAL; 534 } 535 536 shared = dapm_is_shared_kcontrol(dapm, w, &w->kcontrol_news[0], 537 &kcontrol); 538 if (kcontrol) { 539 wlist = kcontrol->private_data; 540 wlistentries = wlist->num_widgets + 1; 541 } else { 542 wlist = NULL; 543 wlistentries = 1; 544 } 545 wlistsize = sizeof(struct snd_soc_dapm_widget_list) + 546 wlistentries * sizeof(struct snd_soc_dapm_widget *), 547 wlist = krealloc(wlist, wlistsize, GFP_KERNEL); 548 if (wlist == NULL) { 549 dev_err(dapm->dev, 550 "asoc: can't allocate widget list for %s\n", w->name); 551 return -ENOMEM; 552 } 553 wlist->num_widgets = wlistentries; 554 wlist->widgets[wlistentries - 1] = w; 555 556 if (!kcontrol) { 557 if (dapm->codec) 558 prefix = dapm->codec->name_prefix; 559 else 560 prefix = NULL; 561 562 if (shared) { 563 name = w->kcontrol_news[0].name; 564 prefix_len = 0; 565 } else { 566 name = w->name; 567 if (prefix) 568 prefix_len = strlen(prefix) + 1; 569 else 570 prefix_len = 0; 571 } 572 573 /* 574 * The control will get a prefix from the control creation 575 * process but we're also using the same prefix for widgets so 576 * cut the prefix off the front of the widget name. 577 */ 578 kcontrol = snd_soc_cnew(&w->kcontrol_news[0], wlist, 579 name + prefix_len, prefix); 580 ret = snd_ctl_add(card, kcontrol); 581 if (ret < 0) { 582 dev_err(dapm->dev, 583 "asoc: failed to add kcontrol %s\n", w->name); 584 kfree(wlist); 585 return ret; 586 } 587 } 588 589 kcontrol->private_data = wlist; 590 591 w->kcontrols[0] = kcontrol; 592 593 list_for_each_entry(path, &w->sources, list_sink) 594 path->kcontrol = kcontrol; 595 596 return 0; 597 } 598 599 /* create new dapm volume control */ 600 static int dapm_new_pga(struct snd_soc_dapm_widget *w) 601 { 602 if (w->num_kcontrols) 603 dev_err(w->dapm->dev, 604 "asoc: PGA controls not supported: '%s'\n", w->name); 605 606 return 0; 607 } 608 609 /* reset 'walked' bit for each dapm path */ 610 static inline void dapm_clear_walk(struct snd_soc_dapm_context *dapm) 611 { 612 struct snd_soc_dapm_path *p; 613 614 list_for_each_entry(p, &dapm->card->paths, list) 615 p->walked = 0; 616 } 617 618 /* We implement power down on suspend by checking the power state of 619 * the ALSA card - when we are suspending the ALSA state for the card 620 * is set to D3. 621 */ 622 static int snd_soc_dapm_suspend_check(struct snd_soc_dapm_widget *widget) 623 { 624 int level = snd_power_get_state(widget->dapm->card->snd_card); 625 626 switch (level) { 627 case SNDRV_CTL_POWER_D3hot: 628 case SNDRV_CTL_POWER_D3cold: 629 if (widget->ignore_suspend) 630 dev_dbg(widget->dapm->dev, "%s ignoring suspend\n", 631 widget->name); 632 return widget->ignore_suspend; 633 default: 634 return 1; 635 } 636 } 637 638 /* 639 * Recursively check for a completed path to an active or physically connected 640 * output widget. Returns number of complete paths. 641 */ 642 static int is_connected_output_ep(struct snd_soc_dapm_widget *widget) 643 { 644 struct snd_soc_dapm_path *path; 645 int con = 0; 646 647 if (widget->id == snd_soc_dapm_supply) 648 return 0; 649 650 switch (widget->id) { 651 case snd_soc_dapm_adc: 652 case snd_soc_dapm_aif_out: 653 if (widget->active) 654 return snd_soc_dapm_suspend_check(widget); 655 default: 656 break; 657 } 658 659 if (widget->connected) { 660 /* connected pin ? */ 661 if (widget->id == snd_soc_dapm_output && !widget->ext) 662 return snd_soc_dapm_suspend_check(widget); 663 664 /* connected jack or spk ? */ 665 if (widget->id == snd_soc_dapm_hp || widget->id == snd_soc_dapm_spk || 666 (widget->id == snd_soc_dapm_line && !list_empty(&widget->sources))) 667 return snd_soc_dapm_suspend_check(widget); 668 } 669 670 list_for_each_entry(path, &widget->sinks, list_source) { 671 if (path->weak) 672 continue; 673 674 if (path->walked) 675 continue; 676 677 if (path->sink && path->connect) { 678 path->walked = 1; 679 con += is_connected_output_ep(path->sink); 680 } 681 } 682 683 return con; 684 } 685 686 /* 687 * Recursively check for a completed path to an active or physically connected 688 * input widget. Returns number of complete paths. 689 */ 690 static int is_connected_input_ep(struct snd_soc_dapm_widget *widget) 691 { 692 struct snd_soc_dapm_path *path; 693 int con = 0; 694 695 if (widget->id == snd_soc_dapm_supply) 696 return 0; 697 698 /* active stream ? */ 699 switch (widget->id) { 700 case snd_soc_dapm_dac: 701 case snd_soc_dapm_aif_in: 702 if (widget->active) 703 return snd_soc_dapm_suspend_check(widget); 704 default: 705 break; 706 } 707 708 if (widget->connected) { 709 /* connected pin ? */ 710 if (widget->id == snd_soc_dapm_input && !widget->ext) 711 return snd_soc_dapm_suspend_check(widget); 712 713 /* connected VMID/Bias for lower pops */ 714 if (widget->id == snd_soc_dapm_vmid) 715 return snd_soc_dapm_suspend_check(widget); 716 717 /* connected jack ? */ 718 if (widget->id == snd_soc_dapm_mic || 719 (widget->id == snd_soc_dapm_line && !list_empty(&widget->sinks))) 720 return snd_soc_dapm_suspend_check(widget); 721 } 722 723 list_for_each_entry(path, &widget->sources, list_sink) { 724 if (path->weak) 725 continue; 726 727 if (path->walked) 728 continue; 729 730 if (path->source && path->connect) { 731 path->walked = 1; 732 con += is_connected_input_ep(path->source); 733 } 734 } 735 736 return con; 737 } 738 739 /* 740 * Handler for generic register modifier widget. 741 */ 742 int dapm_reg_event(struct snd_soc_dapm_widget *w, 743 struct snd_kcontrol *kcontrol, int event) 744 { 745 unsigned int val; 746 747 if (SND_SOC_DAPM_EVENT_ON(event)) 748 val = w->on_val; 749 else 750 val = w->off_val; 751 752 soc_widget_update_bits(w, -(w->reg + 1), 753 w->mask << w->shift, val << w->shift); 754 755 return 0; 756 } 757 EXPORT_SYMBOL_GPL(dapm_reg_event); 758 759 /* Generic check to see if a widget should be powered. 760 */ 761 static int dapm_generic_check_power(struct snd_soc_dapm_widget *w) 762 { 763 int in, out; 764 765 in = is_connected_input_ep(w); 766 dapm_clear_walk(w->dapm); 767 out = is_connected_output_ep(w); 768 dapm_clear_walk(w->dapm); 769 return out != 0 && in != 0; 770 } 771 772 /* Check to see if an ADC has power */ 773 static int dapm_adc_check_power(struct snd_soc_dapm_widget *w) 774 { 775 int in; 776 777 if (w->active) { 778 in = is_connected_input_ep(w); 779 dapm_clear_walk(w->dapm); 780 return in != 0; 781 } else { 782 return dapm_generic_check_power(w); 783 } 784 } 785 786 /* Check to see if a DAC has power */ 787 static int dapm_dac_check_power(struct snd_soc_dapm_widget *w) 788 { 789 int out; 790 791 if (w->active) { 792 out = is_connected_output_ep(w); 793 dapm_clear_walk(w->dapm); 794 return out != 0; 795 } else { 796 return dapm_generic_check_power(w); 797 } 798 } 799 800 /* Check to see if a power supply is needed */ 801 static int dapm_supply_check_power(struct snd_soc_dapm_widget *w) 802 { 803 struct snd_soc_dapm_path *path; 804 int power = 0; 805 806 /* Check if one of our outputs is connected */ 807 list_for_each_entry(path, &w->sinks, list_source) { 808 if (path->weak) 809 continue; 810 811 if (path->connected && 812 !path->connected(path->source, path->sink)) 813 continue; 814 815 if (!path->sink) 816 continue; 817 818 if (path->sink->force) { 819 power = 1; 820 break; 821 } 822 823 if (path->sink->power_check && 824 path->sink->power_check(path->sink)) { 825 power = 1; 826 break; 827 } 828 } 829 830 dapm_clear_walk(w->dapm); 831 832 return power; 833 } 834 835 static int dapm_seq_compare(struct snd_soc_dapm_widget *a, 836 struct snd_soc_dapm_widget *b, 837 bool power_up) 838 { 839 int *sort; 840 841 if (power_up) 842 sort = dapm_up_seq; 843 else 844 sort = dapm_down_seq; 845 846 if (sort[a->id] != sort[b->id]) 847 return sort[a->id] - sort[b->id]; 848 if (a->subseq != b->subseq) { 849 if (power_up) 850 return a->subseq - b->subseq; 851 else 852 return b->subseq - a->subseq; 853 } 854 if (a->reg != b->reg) 855 return a->reg - b->reg; 856 if (a->dapm != b->dapm) 857 return (unsigned long)a->dapm - (unsigned long)b->dapm; 858 859 return 0; 860 } 861 862 /* Insert a widget in order into a DAPM power sequence. */ 863 static void dapm_seq_insert(struct snd_soc_dapm_widget *new_widget, 864 struct list_head *list, 865 bool power_up) 866 { 867 struct snd_soc_dapm_widget *w; 868 869 list_for_each_entry(w, list, power_list) 870 if (dapm_seq_compare(new_widget, w, power_up) < 0) { 871 list_add_tail(&new_widget->power_list, &w->power_list); 872 return; 873 } 874 875 list_add_tail(&new_widget->power_list, list); 876 } 877 878 static void dapm_seq_check_event(struct snd_soc_dapm_context *dapm, 879 struct snd_soc_dapm_widget *w, int event) 880 { 881 struct snd_soc_card *card = dapm->card; 882 const char *ev_name; 883 int power, ret; 884 885 switch (event) { 886 case SND_SOC_DAPM_PRE_PMU: 887 ev_name = "PRE_PMU"; 888 power = 1; 889 break; 890 case SND_SOC_DAPM_POST_PMU: 891 ev_name = "POST_PMU"; 892 power = 1; 893 break; 894 case SND_SOC_DAPM_PRE_PMD: 895 ev_name = "PRE_PMD"; 896 power = 0; 897 break; 898 case SND_SOC_DAPM_POST_PMD: 899 ev_name = "POST_PMD"; 900 power = 0; 901 break; 902 default: 903 BUG(); 904 return; 905 } 906 907 if (w->power != power) 908 return; 909 910 if (w->event && (w->event_flags & event)) { 911 pop_dbg(dapm->dev, card->pop_time, "pop test : %s %s\n", 912 w->name, ev_name); 913 trace_snd_soc_dapm_widget_event_start(w, event); 914 ret = w->event(w, NULL, event); 915 trace_snd_soc_dapm_widget_event_done(w, event); 916 if (ret < 0) 917 pr_err("%s: %s event failed: %d\n", 918 ev_name, w->name, ret); 919 } 920 } 921 922 /* Apply the coalesced changes from a DAPM sequence */ 923 static void dapm_seq_run_coalesced(struct snd_soc_dapm_context *dapm, 924 struct list_head *pending) 925 { 926 struct snd_soc_card *card = dapm->card; 927 struct snd_soc_dapm_widget *w; 928 int reg, power; 929 unsigned int value = 0; 930 unsigned int mask = 0; 931 unsigned int cur_mask; 932 933 reg = list_first_entry(pending, struct snd_soc_dapm_widget, 934 power_list)->reg; 935 936 list_for_each_entry(w, pending, power_list) { 937 cur_mask = 1 << w->shift; 938 BUG_ON(reg != w->reg); 939 940 if (w->invert) 941 power = !w->power; 942 else 943 power = w->power; 944 945 mask |= cur_mask; 946 if (power) 947 value |= cur_mask; 948 949 pop_dbg(dapm->dev, card->pop_time, 950 "pop test : Queue %s: reg=0x%x, 0x%x/0x%x\n", 951 w->name, reg, value, mask); 952 953 /* Check for events */ 954 dapm_seq_check_event(dapm, w, SND_SOC_DAPM_PRE_PMU); 955 dapm_seq_check_event(dapm, w, SND_SOC_DAPM_PRE_PMD); 956 } 957 958 if (reg >= 0) { 959 /* Any widget will do, they should all be updating the 960 * same register. 961 */ 962 w = list_first_entry(pending, struct snd_soc_dapm_widget, 963 power_list); 964 965 pop_dbg(dapm->dev, card->pop_time, 966 "pop test : Applying 0x%x/0x%x to %x in %dms\n", 967 value, mask, reg, card->pop_time); 968 pop_wait(card->pop_time); 969 soc_widget_update_bits(w, reg, mask, value); 970 } 971 972 list_for_each_entry(w, pending, power_list) { 973 dapm_seq_check_event(dapm, w, SND_SOC_DAPM_POST_PMU); 974 dapm_seq_check_event(dapm, w, SND_SOC_DAPM_POST_PMD); 975 } 976 } 977 978 /* Apply a DAPM power sequence. 979 * 980 * We walk over a pre-sorted list of widgets to apply power to. In 981 * order to minimise the number of writes to the device required 982 * multiple widgets will be updated in a single write where possible. 983 * Currently anything that requires more than a single write is not 984 * handled. 985 */ 986 static void dapm_seq_run(struct snd_soc_dapm_context *dapm, 987 struct list_head *list, int event, bool power_up) 988 { 989 struct snd_soc_dapm_widget *w, *n; 990 LIST_HEAD(pending); 991 int cur_sort = -1; 992 int cur_subseq = -1; 993 int cur_reg = SND_SOC_NOPM; 994 struct snd_soc_dapm_context *cur_dapm = NULL; 995 int ret, i; 996 int *sort; 997 998 if (power_up) 999 sort = dapm_up_seq; 1000 else 1001 sort = dapm_down_seq; 1002 1003 list_for_each_entry_safe(w, n, list, power_list) { 1004 ret = 0; 1005 1006 /* Do we need to apply any queued changes? */ 1007 if (sort[w->id] != cur_sort || w->reg != cur_reg || 1008 w->dapm != cur_dapm || w->subseq != cur_subseq) { 1009 if (!list_empty(&pending)) 1010 dapm_seq_run_coalesced(cur_dapm, &pending); 1011 1012 if (cur_dapm && cur_dapm->seq_notifier) { 1013 for (i = 0; i < ARRAY_SIZE(dapm_up_seq); i++) 1014 if (sort[i] == cur_sort) 1015 cur_dapm->seq_notifier(cur_dapm, 1016 i, 1017 cur_subseq); 1018 } 1019 1020 INIT_LIST_HEAD(&pending); 1021 cur_sort = -1; 1022 cur_subseq = INT_MIN; 1023 cur_reg = SND_SOC_NOPM; 1024 cur_dapm = NULL; 1025 } 1026 1027 switch (w->id) { 1028 case snd_soc_dapm_pre: 1029 if (!w->event) 1030 list_for_each_entry_safe_continue(w, n, list, 1031 power_list); 1032 1033 if (event == SND_SOC_DAPM_STREAM_START) 1034 ret = w->event(w, 1035 NULL, SND_SOC_DAPM_PRE_PMU); 1036 else if (event == SND_SOC_DAPM_STREAM_STOP) 1037 ret = w->event(w, 1038 NULL, SND_SOC_DAPM_PRE_PMD); 1039 break; 1040 1041 case snd_soc_dapm_post: 1042 if (!w->event) 1043 list_for_each_entry_safe_continue(w, n, list, 1044 power_list); 1045 1046 if (event == SND_SOC_DAPM_STREAM_START) 1047 ret = w->event(w, 1048 NULL, SND_SOC_DAPM_POST_PMU); 1049 else if (event == SND_SOC_DAPM_STREAM_STOP) 1050 ret = w->event(w, 1051 NULL, SND_SOC_DAPM_POST_PMD); 1052 break; 1053 1054 default: 1055 /* Queue it up for application */ 1056 cur_sort = sort[w->id]; 1057 cur_subseq = w->subseq; 1058 cur_reg = w->reg; 1059 cur_dapm = w->dapm; 1060 list_move(&w->power_list, &pending); 1061 break; 1062 } 1063 1064 if (ret < 0) 1065 dev_err(w->dapm->dev, 1066 "Failed to apply widget power: %d\n", ret); 1067 } 1068 1069 if (!list_empty(&pending)) 1070 dapm_seq_run_coalesced(cur_dapm, &pending); 1071 1072 if (cur_dapm && cur_dapm->seq_notifier) { 1073 for (i = 0; i < ARRAY_SIZE(dapm_up_seq); i++) 1074 if (sort[i] == cur_sort) 1075 cur_dapm->seq_notifier(cur_dapm, 1076 i, cur_subseq); 1077 } 1078 } 1079 1080 static void dapm_widget_update(struct snd_soc_dapm_context *dapm) 1081 { 1082 struct snd_soc_dapm_update *update = dapm->update; 1083 struct snd_soc_dapm_widget *w; 1084 int ret; 1085 1086 if (!update) 1087 return; 1088 1089 w = update->widget; 1090 1091 if (w->event && 1092 (w->event_flags & SND_SOC_DAPM_PRE_REG)) { 1093 ret = w->event(w, update->kcontrol, SND_SOC_DAPM_PRE_REG); 1094 if (ret != 0) 1095 pr_err("%s DAPM pre-event failed: %d\n", 1096 w->name, ret); 1097 } 1098 1099 ret = snd_soc_update_bits(w->codec, update->reg, update->mask, 1100 update->val); 1101 if (ret < 0) 1102 pr_err("%s DAPM update failed: %d\n", w->name, ret); 1103 1104 if (w->event && 1105 (w->event_flags & SND_SOC_DAPM_POST_REG)) { 1106 ret = w->event(w, update->kcontrol, SND_SOC_DAPM_POST_REG); 1107 if (ret != 0) 1108 pr_err("%s DAPM post-event failed: %d\n", 1109 w->name, ret); 1110 } 1111 } 1112 1113 /* Async callback run prior to DAPM sequences - brings to _PREPARE if 1114 * they're changing state. 1115 */ 1116 static void dapm_pre_sequence_async(void *data, async_cookie_t cookie) 1117 { 1118 struct snd_soc_dapm_context *d = data; 1119 int ret; 1120 1121 /* If we're off and we're not supposed to be go into STANDBY */ 1122 if (d->bias_level == SND_SOC_BIAS_OFF && 1123 d->target_bias_level != SND_SOC_BIAS_OFF) { 1124 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_STANDBY); 1125 if (ret != 0) 1126 dev_err(d->dev, 1127 "Failed to turn on bias: %d\n", ret); 1128 } 1129 1130 /* Prepare for a STADDBY->ON or ON->STANDBY transition */ 1131 if (d->bias_level != d->target_bias_level) { 1132 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_PREPARE); 1133 if (ret != 0) 1134 dev_err(d->dev, 1135 "Failed to prepare bias: %d\n", ret); 1136 } 1137 } 1138 1139 /* Async callback run prior to DAPM sequences - brings to their final 1140 * state. 1141 */ 1142 static void dapm_post_sequence_async(void *data, async_cookie_t cookie) 1143 { 1144 struct snd_soc_dapm_context *d = data; 1145 int ret; 1146 1147 /* If we just powered the last thing off drop to standby bias */ 1148 if (d->bias_level == SND_SOC_BIAS_PREPARE && 1149 (d->target_bias_level == SND_SOC_BIAS_STANDBY || 1150 d->target_bias_level == SND_SOC_BIAS_OFF)) { 1151 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_STANDBY); 1152 if (ret != 0) 1153 dev_err(d->dev, "Failed to apply standby bias: %d\n", 1154 ret); 1155 } 1156 1157 /* If we're in standby and can support bias off then do that */ 1158 if (d->bias_level == SND_SOC_BIAS_STANDBY && 1159 d->target_bias_level == SND_SOC_BIAS_OFF) { 1160 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_OFF); 1161 if (ret != 0) 1162 dev_err(d->dev, "Failed to turn off bias: %d\n", ret); 1163 } 1164 1165 /* If we just powered up then move to active bias */ 1166 if (d->bias_level == SND_SOC_BIAS_PREPARE && 1167 d->target_bias_level == SND_SOC_BIAS_ON) { 1168 ret = snd_soc_dapm_set_bias_level(d, SND_SOC_BIAS_ON); 1169 if (ret != 0) 1170 dev_err(d->dev, "Failed to apply active bias: %d\n", 1171 ret); 1172 } 1173 } 1174 1175 /* 1176 * Scan each dapm widget for complete audio path. 1177 * A complete path is a route that has valid endpoints i.e.:- 1178 * 1179 * o DAC to output pin. 1180 * o Input Pin to ADC. 1181 * o Input pin to Output pin (bypass, sidetone) 1182 * o DAC to ADC (loopback). 1183 */ 1184 static int dapm_power_widgets(struct snd_soc_dapm_context *dapm, int event) 1185 { 1186 struct snd_soc_card *card = dapm->card; 1187 struct snd_soc_dapm_widget *w; 1188 struct snd_soc_dapm_context *d; 1189 LIST_HEAD(up_list); 1190 LIST_HEAD(down_list); 1191 LIST_HEAD(async_domain); 1192 enum snd_soc_bias_level bias; 1193 int power; 1194 1195 trace_snd_soc_dapm_start(card); 1196 1197 list_for_each_entry(d, &card->dapm_list, list) { 1198 if (d->n_widgets || d->codec == NULL) { 1199 if (d->idle_bias_off) 1200 d->target_bias_level = SND_SOC_BIAS_OFF; 1201 else 1202 d->target_bias_level = SND_SOC_BIAS_STANDBY; 1203 } 1204 } 1205 1206 /* Check which widgets we need to power and store them in 1207 * lists indicating if they should be powered up or down. 1208 */ 1209 list_for_each_entry(w, &card->widgets, list) { 1210 switch (w->id) { 1211 case snd_soc_dapm_pre: 1212 dapm_seq_insert(w, &down_list, false); 1213 break; 1214 case snd_soc_dapm_post: 1215 dapm_seq_insert(w, &up_list, true); 1216 break; 1217 1218 default: 1219 if (!w->power_check) 1220 continue; 1221 1222 if (!w->force) 1223 power = w->power_check(w); 1224 else 1225 power = 1; 1226 1227 if (power) { 1228 d = w->dapm; 1229 1230 /* Supplies and micbiases only bring 1231 * the context up to STANDBY as unless 1232 * something else is active and 1233 * passing audio they generally don't 1234 * require full power. 1235 */ 1236 switch (w->id) { 1237 case snd_soc_dapm_supply: 1238 case snd_soc_dapm_micbias: 1239 if (d->target_bias_level < SND_SOC_BIAS_STANDBY) 1240 d->target_bias_level = SND_SOC_BIAS_STANDBY; 1241 break; 1242 default: 1243 d->target_bias_level = SND_SOC_BIAS_ON; 1244 break; 1245 } 1246 } 1247 1248 if (w->power == power) 1249 continue; 1250 1251 trace_snd_soc_dapm_widget_power(w, power); 1252 1253 if (power) 1254 dapm_seq_insert(w, &up_list, true); 1255 else 1256 dapm_seq_insert(w, &down_list, false); 1257 1258 w->power = power; 1259 break; 1260 } 1261 } 1262 1263 /* If there are no DAPM widgets then try to figure out power from the 1264 * event type. 1265 */ 1266 if (!dapm->n_widgets) { 1267 switch (event) { 1268 case SND_SOC_DAPM_STREAM_START: 1269 case SND_SOC_DAPM_STREAM_RESUME: 1270 dapm->target_bias_level = SND_SOC_BIAS_ON; 1271 break; 1272 case SND_SOC_DAPM_STREAM_STOP: 1273 if (dapm->codec->active) 1274 dapm->target_bias_level = SND_SOC_BIAS_ON; 1275 else 1276 dapm->target_bias_level = SND_SOC_BIAS_STANDBY; 1277 break; 1278 case SND_SOC_DAPM_STREAM_SUSPEND: 1279 dapm->target_bias_level = SND_SOC_BIAS_STANDBY; 1280 break; 1281 case SND_SOC_DAPM_STREAM_NOP: 1282 dapm->target_bias_level = dapm->bias_level; 1283 break; 1284 default: 1285 break; 1286 } 1287 } 1288 1289 /* Force all contexts in the card to the same bias state */ 1290 bias = SND_SOC_BIAS_OFF; 1291 list_for_each_entry(d, &card->dapm_list, list) 1292 if (d->target_bias_level > bias) 1293 bias = d->target_bias_level; 1294 list_for_each_entry(d, &card->dapm_list, list) 1295 d->target_bias_level = bias; 1296 1297 1298 /* Run all the bias changes in parallel */ 1299 list_for_each_entry(d, &dapm->card->dapm_list, list) 1300 async_schedule_domain(dapm_pre_sequence_async, d, 1301 &async_domain); 1302 async_synchronize_full_domain(&async_domain); 1303 1304 /* Power down widgets first; try to avoid amplifying pops. */ 1305 dapm_seq_run(dapm, &down_list, event, false); 1306 1307 dapm_widget_update(dapm); 1308 1309 /* Now power up. */ 1310 dapm_seq_run(dapm, &up_list, event, true); 1311 1312 /* Run all the bias changes in parallel */ 1313 list_for_each_entry(d, &dapm->card->dapm_list, list) 1314 async_schedule_domain(dapm_post_sequence_async, d, 1315 &async_domain); 1316 async_synchronize_full_domain(&async_domain); 1317 1318 pop_dbg(dapm->dev, card->pop_time, 1319 "DAPM sequencing finished, waiting %dms\n", card->pop_time); 1320 pop_wait(card->pop_time); 1321 1322 trace_snd_soc_dapm_done(card); 1323 1324 return 0; 1325 } 1326 1327 #ifdef CONFIG_DEBUG_FS 1328 static int dapm_widget_power_open_file(struct inode *inode, struct file *file) 1329 { 1330 file->private_data = inode->i_private; 1331 return 0; 1332 } 1333 1334 static ssize_t dapm_widget_power_read_file(struct file *file, 1335 char __user *user_buf, 1336 size_t count, loff_t *ppos) 1337 { 1338 struct snd_soc_dapm_widget *w = file->private_data; 1339 char *buf; 1340 int in, out; 1341 ssize_t ret; 1342 struct snd_soc_dapm_path *p = NULL; 1343 1344 buf = kmalloc(PAGE_SIZE, GFP_KERNEL); 1345 if (!buf) 1346 return -ENOMEM; 1347 1348 in = is_connected_input_ep(w); 1349 dapm_clear_walk(w->dapm); 1350 out = is_connected_output_ep(w); 1351 dapm_clear_walk(w->dapm); 1352 1353 ret = snprintf(buf, PAGE_SIZE, "%s: %s in %d out %d", 1354 w->name, w->power ? "On" : "Off", in, out); 1355 1356 if (w->reg >= 0) 1357 ret += snprintf(buf + ret, PAGE_SIZE - ret, 1358 " - R%d(0x%x) bit %d", 1359 w->reg, w->reg, w->shift); 1360 1361 ret += snprintf(buf + ret, PAGE_SIZE - ret, "\n"); 1362 1363 if (w->sname) 1364 ret += snprintf(buf + ret, PAGE_SIZE - ret, " stream %s %s\n", 1365 w->sname, 1366 w->active ? "active" : "inactive"); 1367 1368 list_for_each_entry(p, &w->sources, list_sink) { 1369 if (p->connected && !p->connected(w, p->sink)) 1370 continue; 1371 1372 if (p->connect) 1373 ret += snprintf(buf + ret, PAGE_SIZE - ret, 1374 " in \"%s\" \"%s\"\n", 1375 p->name ? p->name : "static", 1376 p->source->name); 1377 } 1378 list_for_each_entry(p, &w->sinks, list_source) { 1379 if (p->connected && !p->connected(w, p->sink)) 1380 continue; 1381 1382 if (p->connect) 1383 ret += snprintf(buf + ret, PAGE_SIZE - ret, 1384 " out \"%s\" \"%s\"\n", 1385 p->name ? p->name : "static", 1386 p->sink->name); 1387 } 1388 1389 ret = simple_read_from_buffer(user_buf, count, ppos, buf, ret); 1390 1391 kfree(buf); 1392 return ret; 1393 } 1394 1395 static const struct file_operations dapm_widget_power_fops = { 1396 .open = dapm_widget_power_open_file, 1397 .read = dapm_widget_power_read_file, 1398 .llseek = default_llseek, 1399 }; 1400 1401 static int dapm_bias_open_file(struct inode *inode, struct file *file) 1402 { 1403 file->private_data = inode->i_private; 1404 return 0; 1405 } 1406 1407 static ssize_t dapm_bias_read_file(struct file *file, char __user *user_buf, 1408 size_t count, loff_t *ppos) 1409 { 1410 struct snd_soc_dapm_context *dapm = file->private_data; 1411 char *level; 1412 1413 switch (dapm->bias_level) { 1414 case SND_SOC_BIAS_ON: 1415 level = "On\n"; 1416 break; 1417 case SND_SOC_BIAS_PREPARE: 1418 level = "Prepare\n"; 1419 break; 1420 case SND_SOC_BIAS_STANDBY: 1421 level = "Standby\n"; 1422 break; 1423 case SND_SOC_BIAS_OFF: 1424 level = "Off\n"; 1425 break; 1426 default: 1427 BUG(); 1428 level = "Unknown\n"; 1429 break; 1430 } 1431 1432 return simple_read_from_buffer(user_buf, count, ppos, level, 1433 strlen(level)); 1434 } 1435 1436 static const struct file_operations dapm_bias_fops = { 1437 .open = dapm_bias_open_file, 1438 .read = dapm_bias_read_file, 1439 .llseek = default_llseek, 1440 }; 1441 1442 void snd_soc_dapm_debugfs_init(struct snd_soc_dapm_context *dapm, 1443 struct dentry *parent) 1444 { 1445 struct dentry *d; 1446 1447 dapm->debugfs_dapm = debugfs_create_dir("dapm", parent); 1448 1449 if (!dapm->debugfs_dapm) { 1450 printk(KERN_WARNING 1451 "Failed to create DAPM debugfs directory\n"); 1452 return; 1453 } 1454 1455 d = debugfs_create_file("bias_level", 0444, 1456 dapm->debugfs_dapm, dapm, 1457 &dapm_bias_fops); 1458 if (!d) 1459 dev_warn(dapm->dev, 1460 "ASoC: Failed to create bias level debugfs file\n"); 1461 } 1462 1463 static void dapm_debugfs_add_widget(struct snd_soc_dapm_widget *w) 1464 { 1465 struct snd_soc_dapm_context *dapm = w->dapm; 1466 struct dentry *d; 1467 1468 if (!dapm->debugfs_dapm || !w->name) 1469 return; 1470 1471 d = debugfs_create_file(w->name, 0444, 1472 dapm->debugfs_dapm, w, 1473 &dapm_widget_power_fops); 1474 if (!d) 1475 dev_warn(w->dapm->dev, 1476 "ASoC: Failed to create %s debugfs file\n", 1477 w->name); 1478 } 1479 1480 static void dapm_debugfs_cleanup(struct snd_soc_dapm_context *dapm) 1481 { 1482 debugfs_remove_recursive(dapm->debugfs_dapm); 1483 } 1484 1485 #else 1486 void snd_soc_dapm_debugfs_init(struct snd_soc_dapm_context *dapm, 1487 struct dentry *parent) 1488 { 1489 } 1490 1491 static inline void dapm_debugfs_add_widget(struct snd_soc_dapm_widget *w) 1492 { 1493 } 1494 1495 static inline void dapm_debugfs_cleanup(struct snd_soc_dapm_context *dapm) 1496 { 1497 } 1498 1499 #endif 1500 1501 /* test and update the power status of a mux widget */ 1502 static int dapm_mux_update_power(struct snd_soc_dapm_widget *widget, 1503 struct snd_kcontrol *kcontrol, int change, 1504 int mux, struct soc_enum *e) 1505 { 1506 struct snd_soc_dapm_path *path; 1507 int found = 0; 1508 1509 if (widget->id != snd_soc_dapm_mux && 1510 widget->id != snd_soc_dapm_virt_mux && 1511 widget->id != snd_soc_dapm_value_mux) 1512 return -ENODEV; 1513 1514 if (!change) 1515 return 0; 1516 1517 /* find dapm widget path assoc with kcontrol */ 1518 list_for_each_entry(path, &widget->dapm->card->paths, list) { 1519 if (path->kcontrol != kcontrol) 1520 continue; 1521 1522 if (!path->name || !e->texts[mux]) 1523 continue; 1524 1525 found = 1; 1526 /* we now need to match the string in the enum to the path */ 1527 if (!(strcmp(path->name, e->texts[mux]))) 1528 path->connect = 1; /* new connection */ 1529 else 1530 path->connect = 0; /* old connection must be powered down */ 1531 } 1532 1533 if (found) 1534 dapm_power_widgets(widget->dapm, SND_SOC_DAPM_STREAM_NOP); 1535 1536 return 0; 1537 } 1538 1539 /* test and update the power status of a mixer or switch widget */ 1540 static int dapm_mixer_update_power(struct snd_soc_dapm_widget *widget, 1541 struct snd_kcontrol *kcontrol, int connect) 1542 { 1543 struct snd_soc_dapm_path *path; 1544 int found = 0; 1545 1546 if (widget->id != snd_soc_dapm_mixer && 1547 widget->id != snd_soc_dapm_mixer_named_ctl && 1548 widget->id != snd_soc_dapm_switch) 1549 return -ENODEV; 1550 1551 /* find dapm widget path assoc with kcontrol */ 1552 list_for_each_entry(path, &widget->dapm->card->paths, list) { 1553 if (path->kcontrol != kcontrol) 1554 continue; 1555 1556 /* found, now check type */ 1557 found = 1; 1558 path->connect = connect; 1559 break; 1560 } 1561 1562 if (found) 1563 dapm_power_widgets(widget->dapm, SND_SOC_DAPM_STREAM_NOP); 1564 1565 return 0; 1566 } 1567 1568 /* show dapm widget status in sys fs */ 1569 static ssize_t dapm_widget_show(struct device *dev, 1570 struct device_attribute *attr, char *buf) 1571 { 1572 struct snd_soc_pcm_runtime *rtd = 1573 container_of(dev, struct snd_soc_pcm_runtime, dev); 1574 struct snd_soc_codec *codec =rtd->codec; 1575 struct snd_soc_dapm_widget *w; 1576 int count = 0; 1577 char *state = "not set"; 1578 1579 list_for_each_entry(w, &codec->card->widgets, list) { 1580 if (w->dapm != &codec->dapm) 1581 continue; 1582 1583 /* only display widgets that burnm power */ 1584 switch (w->id) { 1585 case snd_soc_dapm_hp: 1586 case snd_soc_dapm_mic: 1587 case snd_soc_dapm_spk: 1588 case snd_soc_dapm_line: 1589 case snd_soc_dapm_micbias: 1590 case snd_soc_dapm_dac: 1591 case snd_soc_dapm_adc: 1592 case snd_soc_dapm_pga: 1593 case snd_soc_dapm_out_drv: 1594 case snd_soc_dapm_mixer: 1595 case snd_soc_dapm_mixer_named_ctl: 1596 case snd_soc_dapm_supply: 1597 if (w->name) 1598 count += sprintf(buf + count, "%s: %s\n", 1599 w->name, w->power ? "On":"Off"); 1600 break; 1601 default: 1602 break; 1603 } 1604 } 1605 1606 switch (codec->dapm.bias_level) { 1607 case SND_SOC_BIAS_ON: 1608 state = "On"; 1609 break; 1610 case SND_SOC_BIAS_PREPARE: 1611 state = "Prepare"; 1612 break; 1613 case SND_SOC_BIAS_STANDBY: 1614 state = "Standby"; 1615 break; 1616 case SND_SOC_BIAS_OFF: 1617 state = "Off"; 1618 break; 1619 } 1620 count += sprintf(buf + count, "PM State: %s\n", state); 1621 1622 return count; 1623 } 1624 1625 static DEVICE_ATTR(dapm_widget, 0444, dapm_widget_show, NULL); 1626 1627 int snd_soc_dapm_sys_add(struct device *dev) 1628 { 1629 return device_create_file(dev, &dev_attr_dapm_widget); 1630 } 1631 1632 static void snd_soc_dapm_sys_remove(struct device *dev) 1633 { 1634 device_remove_file(dev, &dev_attr_dapm_widget); 1635 } 1636 1637 /* free all dapm widgets and resources */ 1638 static void dapm_free_widgets(struct snd_soc_dapm_context *dapm) 1639 { 1640 struct snd_soc_dapm_widget *w, *next_w; 1641 struct snd_soc_dapm_path *p, *next_p; 1642 1643 list_for_each_entry_safe(w, next_w, &dapm->card->widgets, list) { 1644 if (w->dapm != dapm) 1645 continue; 1646 list_del(&w->list); 1647 /* 1648 * remove source and sink paths associated to this widget. 1649 * While removing the path, remove reference to it from both 1650 * source and sink widgets so that path is removed only once. 1651 */ 1652 list_for_each_entry_safe(p, next_p, &w->sources, list_sink) { 1653 list_del(&p->list_sink); 1654 list_del(&p->list_source); 1655 list_del(&p->list); 1656 kfree(p->long_name); 1657 kfree(p); 1658 } 1659 list_for_each_entry_safe(p, next_p, &w->sinks, list_source) { 1660 list_del(&p->list_sink); 1661 list_del(&p->list_source); 1662 list_del(&p->list); 1663 kfree(p->long_name); 1664 kfree(p); 1665 } 1666 kfree(w->kcontrols); 1667 kfree(w->name); 1668 kfree(w); 1669 } 1670 } 1671 1672 static struct snd_soc_dapm_widget *dapm_find_widget( 1673 struct snd_soc_dapm_context *dapm, const char *pin, 1674 bool search_other_contexts) 1675 { 1676 struct snd_soc_dapm_widget *w; 1677 struct snd_soc_dapm_widget *fallback = NULL; 1678 1679 list_for_each_entry(w, &dapm->card->widgets, list) { 1680 if (!strcmp(w->name, pin)) { 1681 if (w->dapm == dapm) 1682 return w; 1683 else 1684 fallback = w; 1685 } 1686 } 1687 1688 if (search_other_contexts) 1689 return fallback; 1690 1691 return NULL; 1692 } 1693 1694 static int snd_soc_dapm_set_pin(struct snd_soc_dapm_context *dapm, 1695 const char *pin, int status) 1696 { 1697 struct snd_soc_dapm_widget *w = dapm_find_widget(dapm, pin, true); 1698 1699 if (!w) { 1700 dev_err(dapm->dev, "dapm: unknown pin %s\n", pin); 1701 return -EINVAL; 1702 } 1703 1704 w->connected = status; 1705 if (status == 0) 1706 w->force = 0; 1707 1708 return 0; 1709 } 1710 1711 /** 1712 * snd_soc_dapm_sync - scan and power dapm paths 1713 * @dapm: DAPM context 1714 * 1715 * Walks all dapm audio paths and powers widgets according to their 1716 * stream or path usage. 1717 * 1718 * Returns 0 for success. 1719 */ 1720 int snd_soc_dapm_sync(struct snd_soc_dapm_context *dapm) 1721 { 1722 return dapm_power_widgets(dapm, SND_SOC_DAPM_STREAM_NOP); 1723 } 1724 EXPORT_SYMBOL_GPL(snd_soc_dapm_sync); 1725 1726 static int snd_soc_dapm_add_route(struct snd_soc_dapm_context *dapm, 1727 const struct snd_soc_dapm_route *route) 1728 { 1729 struct snd_soc_dapm_path *path; 1730 struct snd_soc_dapm_widget *wsource = NULL, *wsink = NULL, *w; 1731 struct snd_soc_dapm_widget *wtsource = NULL, *wtsink = NULL; 1732 const char *sink; 1733 const char *control = route->control; 1734 const char *source; 1735 char prefixed_sink[80]; 1736 char prefixed_source[80]; 1737 int ret = 0; 1738 1739 if (dapm->codec && dapm->codec->name_prefix) { 1740 snprintf(prefixed_sink, sizeof(prefixed_sink), "%s %s", 1741 dapm->codec->name_prefix, route->sink); 1742 sink = prefixed_sink; 1743 snprintf(prefixed_source, sizeof(prefixed_source), "%s %s", 1744 dapm->codec->name_prefix, route->source); 1745 source = prefixed_source; 1746 } else { 1747 sink = route->sink; 1748 source = route->source; 1749 } 1750 1751 /* 1752 * find src and dest widgets over all widgets but favor a widget from 1753 * current DAPM context 1754 */ 1755 list_for_each_entry(w, &dapm->card->widgets, list) { 1756 if (!wsink && !(strcmp(w->name, sink))) { 1757 wtsink = w; 1758 if (w->dapm == dapm) 1759 wsink = w; 1760 continue; 1761 } 1762 if (!wsource && !(strcmp(w->name, source))) { 1763 wtsource = w; 1764 if (w->dapm == dapm) 1765 wsource = w; 1766 } 1767 } 1768 /* use widget from another DAPM context if not found from this */ 1769 if (!wsink) 1770 wsink = wtsink; 1771 if (!wsource) 1772 wsource = wtsource; 1773 1774 if (wsource == NULL || wsink == NULL) 1775 return -ENODEV; 1776 1777 path = kzalloc(sizeof(struct snd_soc_dapm_path), GFP_KERNEL); 1778 if (!path) 1779 return -ENOMEM; 1780 1781 path->source = wsource; 1782 path->sink = wsink; 1783 path->connected = route->connected; 1784 INIT_LIST_HEAD(&path->list); 1785 INIT_LIST_HEAD(&path->list_source); 1786 INIT_LIST_HEAD(&path->list_sink); 1787 1788 /* check for external widgets */ 1789 if (wsink->id == snd_soc_dapm_input) { 1790 if (wsource->id == snd_soc_dapm_micbias || 1791 wsource->id == snd_soc_dapm_mic || 1792 wsource->id == snd_soc_dapm_line || 1793 wsource->id == snd_soc_dapm_output) 1794 wsink->ext = 1; 1795 } 1796 if (wsource->id == snd_soc_dapm_output) { 1797 if (wsink->id == snd_soc_dapm_spk || 1798 wsink->id == snd_soc_dapm_hp || 1799 wsink->id == snd_soc_dapm_line || 1800 wsink->id == snd_soc_dapm_input) 1801 wsource->ext = 1; 1802 } 1803 1804 /* connect static paths */ 1805 if (control == NULL) { 1806 list_add(&path->list, &dapm->card->paths); 1807 list_add(&path->list_sink, &wsink->sources); 1808 list_add(&path->list_source, &wsource->sinks); 1809 path->connect = 1; 1810 return 0; 1811 } 1812 1813 /* connect dynamic paths */ 1814 switch (wsink->id) { 1815 case snd_soc_dapm_adc: 1816 case snd_soc_dapm_dac: 1817 case snd_soc_dapm_pga: 1818 case snd_soc_dapm_out_drv: 1819 case snd_soc_dapm_input: 1820 case snd_soc_dapm_output: 1821 case snd_soc_dapm_micbias: 1822 case snd_soc_dapm_vmid: 1823 case snd_soc_dapm_pre: 1824 case snd_soc_dapm_post: 1825 case snd_soc_dapm_supply: 1826 case snd_soc_dapm_aif_in: 1827 case snd_soc_dapm_aif_out: 1828 list_add(&path->list, &dapm->card->paths); 1829 list_add(&path->list_sink, &wsink->sources); 1830 list_add(&path->list_source, &wsource->sinks); 1831 path->connect = 1; 1832 return 0; 1833 case snd_soc_dapm_mux: 1834 case snd_soc_dapm_virt_mux: 1835 case snd_soc_dapm_value_mux: 1836 ret = dapm_connect_mux(dapm, wsource, wsink, path, control, 1837 &wsink->kcontrol_news[0]); 1838 if (ret != 0) 1839 goto err; 1840 break; 1841 case snd_soc_dapm_switch: 1842 case snd_soc_dapm_mixer: 1843 case snd_soc_dapm_mixer_named_ctl: 1844 ret = dapm_connect_mixer(dapm, wsource, wsink, path, control); 1845 if (ret != 0) 1846 goto err; 1847 break; 1848 case snd_soc_dapm_hp: 1849 case snd_soc_dapm_mic: 1850 case snd_soc_dapm_line: 1851 case snd_soc_dapm_spk: 1852 list_add(&path->list, &dapm->card->paths); 1853 list_add(&path->list_sink, &wsink->sources); 1854 list_add(&path->list_source, &wsource->sinks); 1855 path->connect = 0; 1856 return 0; 1857 } 1858 return 0; 1859 1860 err: 1861 dev_warn(dapm->dev, "asoc: no dapm match for %s --> %s --> %s\n", 1862 source, control, sink); 1863 kfree(path); 1864 return ret; 1865 } 1866 1867 /** 1868 * snd_soc_dapm_add_routes - Add routes between DAPM widgets 1869 * @dapm: DAPM context 1870 * @route: audio routes 1871 * @num: number of routes 1872 * 1873 * Connects 2 dapm widgets together via a named audio path. The sink is 1874 * the widget receiving the audio signal, whilst the source is the sender 1875 * of the audio signal. 1876 * 1877 * Returns 0 for success else error. On error all resources can be freed 1878 * with a call to snd_soc_card_free(). 1879 */ 1880 int snd_soc_dapm_add_routes(struct snd_soc_dapm_context *dapm, 1881 const struct snd_soc_dapm_route *route, int num) 1882 { 1883 int i, ret; 1884 1885 for (i = 0; i < num; i++) { 1886 ret = snd_soc_dapm_add_route(dapm, route); 1887 if (ret < 0) { 1888 dev_err(dapm->dev, "Failed to add route %s->%s\n", 1889 route->source, route->sink); 1890 return ret; 1891 } 1892 route++; 1893 } 1894 1895 return 0; 1896 } 1897 EXPORT_SYMBOL_GPL(snd_soc_dapm_add_routes); 1898 1899 static int snd_soc_dapm_weak_route(struct snd_soc_dapm_context *dapm, 1900 const struct snd_soc_dapm_route *route) 1901 { 1902 struct snd_soc_dapm_widget *source = dapm_find_widget(dapm, 1903 route->source, 1904 true); 1905 struct snd_soc_dapm_widget *sink = dapm_find_widget(dapm, 1906 route->sink, 1907 true); 1908 struct snd_soc_dapm_path *path; 1909 int count = 0; 1910 1911 if (!source) { 1912 dev_err(dapm->dev, "Unable to find source %s for weak route\n", 1913 route->source); 1914 return -ENODEV; 1915 } 1916 1917 if (!sink) { 1918 dev_err(dapm->dev, "Unable to find sink %s for weak route\n", 1919 route->sink); 1920 return -ENODEV; 1921 } 1922 1923 if (route->control || route->connected) 1924 dev_warn(dapm->dev, "Ignoring control for weak route %s->%s\n", 1925 route->source, route->sink); 1926 1927 list_for_each_entry(path, &source->sinks, list_source) { 1928 if (path->sink == sink) { 1929 path->weak = 1; 1930 count++; 1931 } 1932 } 1933 1934 if (count == 0) 1935 dev_err(dapm->dev, "No path found for weak route %s->%s\n", 1936 route->source, route->sink); 1937 if (count > 1) 1938 dev_warn(dapm->dev, "%d paths found for weak route %s->%s\n", 1939 count, route->source, route->sink); 1940 1941 return 0; 1942 } 1943 1944 /** 1945 * snd_soc_dapm_weak_routes - Mark routes between DAPM widgets as weak 1946 * @dapm: DAPM context 1947 * @route: audio routes 1948 * @num: number of routes 1949 * 1950 * Mark existing routes matching those specified in the passed array 1951 * as being weak, meaning that they are ignored for the purpose of 1952 * power decisions. The main intended use case is for sidetone paths 1953 * which couple audio between other independent paths if they are both 1954 * active in order to make the combination work better at the user 1955 * level but which aren't intended to be "used". 1956 * 1957 * Note that CODEC drivers should not use this as sidetone type paths 1958 * can frequently also be used as bypass paths. 1959 */ 1960 int snd_soc_dapm_weak_routes(struct snd_soc_dapm_context *dapm, 1961 const struct snd_soc_dapm_route *route, int num) 1962 { 1963 int i, err; 1964 int ret = 0; 1965 1966 for (i = 0; i < num; i++) { 1967 err = snd_soc_dapm_weak_route(dapm, route); 1968 if (err) 1969 ret = err; 1970 route++; 1971 } 1972 1973 return ret; 1974 } 1975 EXPORT_SYMBOL_GPL(snd_soc_dapm_weak_routes); 1976 1977 /** 1978 * snd_soc_dapm_new_widgets - add new dapm widgets 1979 * @dapm: DAPM context 1980 * 1981 * Checks the codec for any new dapm widgets and creates them if found. 1982 * 1983 * Returns 0 for success. 1984 */ 1985 int snd_soc_dapm_new_widgets(struct snd_soc_dapm_context *dapm) 1986 { 1987 struct snd_soc_dapm_widget *w; 1988 unsigned int val; 1989 1990 list_for_each_entry(w, &dapm->card->widgets, list) 1991 { 1992 if (w->new) 1993 continue; 1994 1995 if (w->num_kcontrols) { 1996 w->kcontrols = kzalloc(w->num_kcontrols * 1997 sizeof(struct snd_kcontrol *), 1998 GFP_KERNEL); 1999 if (!w->kcontrols) 2000 return -ENOMEM; 2001 } 2002 2003 switch(w->id) { 2004 case snd_soc_dapm_switch: 2005 case snd_soc_dapm_mixer: 2006 case snd_soc_dapm_mixer_named_ctl: 2007 w->power_check = dapm_generic_check_power; 2008 dapm_new_mixer(w); 2009 break; 2010 case snd_soc_dapm_mux: 2011 case snd_soc_dapm_virt_mux: 2012 case snd_soc_dapm_value_mux: 2013 w->power_check = dapm_generic_check_power; 2014 dapm_new_mux(w); 2015 break; 2016 case snd_soc_dapm_adc: 2017 case snd_soc_dapm_aif_out: 2018 w->power_check = dapm_adc_check_power; 2019 break; 2020 case snd_soc_dapm_dac: 2021 case snd_soc_dapm_aif_in: 2022 w->power_check = dapm_dac_check_power; 2023 break; 2024 case snd_soc_dapm_pga: 2025 case snd_soc_dapm_out_drv: 2026 w->power_check = dapm_generic_check_power; 2027 dapm_new_pga(w); 2028 break; 2029 case snd_soc_dapm_input: 2030 case snd_soc_dapm_output: 2031 case snd_soc_dapm_micbias: 2032 case snd_soc_dapm_spk: 2033 case snd_soc_dapm_hp: 2034 case snd_soc_dapm_mic: 2035 case snd_soc_dapm_line: 2036 w->power_check = dapm_generic_check_power; 2037 break; 2038 case snd_soc_dapm_supply: 2039 w->power_check = dapm_supply_check_power; 2040 case snd_soc_dapm_vmid: 2041 case snd_soc_dapm_pre: 2042 case snd_soc_dapm_post: 2043 break; 2044 } 2045 2046 /* Read the initial power state from the device */ 2047 if (w->reg >= 0) { 2048 val = soc_widget_read(w, w->reg); 2049 val &= 1 << w->shift; 2050 if (w->invert) 2051 val = !val; 2052 2053 if (val) 2054 w->power = 1; 2055 } 2056 2057 w->new = 1; 2058 2059 dapm_debugfs_add_widget(w); 2060 } 2061 2062 dapm_power_widgets(dapm, SND_SOC_DAPM_STREAM_NOP); 2063 return 0; 2064 } 2065 EXPORT_SYMBOL_GPL(snd_soc_dapm_new_widgets); 2066 2067 /** 2068 * snd_soc_dapm_get_volsw - dapm mixer get callback 2069 * @kcontrol: mixer control 2070 * @ucontrol: control element information 2071 * 2072 * Callback to get the value of a dapm mixer control. 2073 * 2074 * Returns 0 for success. 2075 */ 2076 int snd_soc_dapm_get_volsw(struct snd_kcontrol *kcontrol, 2077 struct snd_ctl_elem_value *ucontrol) 2078 { 2079 struct snd_soc_dapm_widget_list *wlist = snd_kcontrol_chip(kcontrol); 2080 struct snd_soc_dapm_widget *widget = wlist->widgets[0]; 2081 struct soc_mixer_control *mc = 2082 (struct soc_mixer_control *)kcontrol->private_value; 2083 unsigned int reg = mc->reg; 2084 unsigned int shift = mc->shift; 2085 unsigned int rshift = mc->rshift; 2086 int max = mc->max; 2087 unsigned int invert = mc->invert; 2088 unsigned int mask = (1 << fls(max)) - 1; 2089 2090 ucontrol->value.integer.value[0] = 2091 (snd_soc_read(widget->codec, reg) >> shift) & mask; 2092 if (shift != rshift) 2093 ucontrol->value.integer.value[1] = 2094 (snd_soc_read(widget->codec, reg) >> rshift) & mask; 2095 if (invert) { 2096 ucontrol->value.integer.value[0] = 2097 max - ucontrol->value.integer.value[0]; 2098 if (shift != rshift) 2099 ucontrol->value.integer.value[1] = 2100 max - ucontrol->value.integer.value[1]; 2101 } 2102 2103 return 0; 2104 } 2105 EXPORT_SYMBOL_GPL(snd_soc_dapm_get_volsw); 2106 2107 /** 2108 * snd_soc_dapm_put_volsw - dapm mixer set callback 2109 * @kcontrol: mixer control 2110 * @ucontrol: control element information 2111 * 2112 * Callback to set the value of a dapm mixer control. 2113 * 2114 * Returns 0 for success. 2115 */ 2116 int snd_soc_dapm_put_volsw(struct snd_kcontrol *kcontrol, 2117 struct snd_ctl_elem_value *ucontrol) 2118 { 2119 struct snd_soc_dapm_widget_list *wlist = snd_kcontrol_chip(kcontrol); 2120 struct snd_soc_dapm_widget *widget = wlist->widgets[0]; 2121 struct snd_soc_codec *codec = widget->codec; 2122 struct soc_mixer_control *mc = 2123 (struct soc_mixer_control *)kcontrol->private_value; 2124 unsigned int reg = mc->reg; 2125 unsigned int shift = mc->shift; 2126 int max = mc->max; 2127 unsigned int mask = (1 << fls(max)) - 1; 2128 unsigned int invert = mc->invert; 2129 unsigned int val; 2130 int connect, change; 2131 struct snd_soc_dapm_update update; 2132 int wi; 2133 2134 val = (ucontrol->value.integer.value[0] & mask); 2135 2136 if (invert) 2137 val = max - val; 2138 mask = mask << shift; 2139 val = val << shift; 2140 2141 if (val) 2142 /* new connection */ 2143 connect = invert ? 0 : 1; 2144 else 2145 /* old connection must be powered down */ 2146 connect = invert ? 1 : 0; 2147 2148 mutex_lock(&codec->mutex); 2149 2150 change = snd_soc_test_bits(widget->codec, reg, mask, val); 2151 if (change) { 2152 for (wi = 0; wi < wlist->num_widgets; wi++) { 2153 widget = wlist->widgets[wi]; 2154 2155 widget->value = val; 2156 2157 update.kcontrol = kcontrol; 2158 update.widget = widget; 2159 update.reg = reg; 2160 update.mask = mask; 2161 update.val = val; 2162 widget->dapm->update = &update; 2163 2164 dapm_mixer_update_power(widget, kcontrol, connect); 2165 2166 widget->dapm->update = NULL; 2167 } 2168 } 2169 2170 mutex_unlock(&codec->mutex); 2171 return 0; 2172 } 2173 EXPORT_SYMBOL_GPL(snd_soc_dapm_put_volsw); 2174 2175 /** 2176 * snd_soc_dapm_get_enum_double - dapm enumerated double mixer get callback 2177 * @kcontrol: mixer control 2178 * @ucontrol: control element information 2179 * 2180 * Callback to get the value of a dapm enumerated double mixer control. 2181 * 2182 * Returns 0 for success. 2183 */ 2184 int snd_soc_dapm_get_enum_double(struct snd_kcontrol *kcontrol, 2185 struct snd_ctl_elem_value *ucontrol) 2186 { 2187 struct snd_soc_dapm_widget_list *wlist = snd_kcontrol_chip(kcontrol); 2188 struct snd_soc_dapm_widget *widget = wlist->widgets[0]; 2189 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 2190 unsigned int val, bitmask; 2191 2192 for (bitmask = 1; bitmask < e->max; bitmask <<= 1) 2193 ; 2194 val = snd_soc_read(widget->codec, e->reg); 2195 ucontrol->value.enumerated.item[0] = (val >> e->shift_l) & (bitmask - 1); 2196 if (e->shift_l != e->shift_r) 2197 ucontrol->value.enumerated.item[1] = 2198 (val >> e->shift_r) & (bitmask - 1); 2199 2200 return 0; 2201 } 2202 EXPORT_SYMBOL_GPL(snd_soc_dapm_get_enum_double); 2203 2204 /** 2205 * snd_soc_dapm_put_enum_double - dapm enumerated double mixer set callback 2206 * @kcontrol: mixer control 2207 * @ucontrol: control element information 2208 * 2209 * Callback to set the value of a dapm enumerated double mixer control. 2210 * 2211 * Returns 0 for success. 2212 */ 2213 int snd_soc_dapm_put_enum_double(struct snd_kcontrol *kcontrol, 2214 struct snd_ctl_elem_value *ucontrol) 2215 { 2216 struct snd_soc_dapm_widget_list *wlist = snd_kcontrol_chip(kcontrol); 2217 struct snd_soc_dapm_widget *widget = wlist->widgets[0]; 2218 struct snd_soc_codec *codec = widget->codec; 2219 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 2220 unsigned int val, mux, change; 2221 unsigned int mask, bitmask; 2222 struct snd_soc_dapm_update update; 2223 int wi; 2224 2225 for (bitmask = 1; bitmask < e->max; bitmask <<= 1) 2226 ; 2227 if (ucontrol->value.enumerated.item[0] > e->max - 1) 2228 return -EINVAL; 2229 mux = ucontrol->value.enumerated.item[0]; 2230 val = mux << e->shift_l; 2231 mask = (bitmask - 1) << e->shift_l; 2232 if (e->shift_l != e->shift_r) { 2233 if (ucontrol->value.enumerated.item[1] > e->max - 1) 2234 return -EINVAL; 2235 val |= ucontrol->value.enumerated.item[1] << e->shift_r; 2236 mask |= (bitmask - 1) << e->shift_r; 2237 } 2238 2239 mutex_lock(&codec->mutex); 2240 2241 change = snd_soc_test_bits(widget->codec, e->reg, mask, val); 2242 if (change) { 2243 for (wi = 0; wi < wlist->num_widgets; wi++) { 2244 widget = wlist->widgets[wi]; 2245 2246 widget->value = val; 2247 2248 update.kcontrol = kcontrol; 2249 update.widget = widget; 2250 update.reg = e->reg; 2251 update.mask = mask; 2252 update.val = val; 2253 widget->dapm->update = &update; 2254 2255 dapm_mux_update_power(widget, kcontrol, change, mux, e); 2256 2257 widget->dapm->update = NULL; 2258 } 2259 } 2260 2261 mutex_unlock(&codec->mutex); 2262 return change; 2263 } 2264 EXPORT_SYMBOL_GPL(snd_soc_dapm_put_enum_double); 2265 2266 /** 2267 * snd_soc_dapm_get_enum_virt - Get virtual DAPM mux 2268 * @kcontrol: mixer control 2269 * @ucontrol: control element information 2270 * 2271 * Returns 0 for success. 2272 */ 2273 int snd_soc_dapm_get_enum_virt(struct snd_kcontrol *kcontrol, 2274 struct snd_ctl_elem_value *ucontrol) 2275 { 2276 struct snd_soc_dapm_widget_list *wlist = snd_kcontrol_chip(kcontrol); 2277 struct snd_soc_dapm_widget *widget = wlist->widgets[0]; 2278 2279 ucontrol->value.enumerated.item[0] = widget->value; 2280 2281 return 0; 2282 } 2283 EXPORT_SYMBOL_GPL(snd_soc_dapm_get_enum_virt); 2284 2285 /** 2286 * snd_soc_dapm_put_enum_virt - Set virtual DAPM mux 2287 * @kcontrol: mixer control 2288 * @ucontrol: control element information 2289 * 2290 * Returns 0 for success. 2291 */ 2292 int snd_soc_dapm_put_enum_virt(struct snd_kcontrol *kcontrol, 2293 struct snd_ctl_elem_value *ucontrol) 2294 { 2295 struct snd_soc_dapm_widget_list *wlist = snd_kcontrol_chip(kcontrol); 2296 struct snd_soc_dapm_widget *widget = wlist->widgets[0]; 2297 struct snd_soc_codec *codec = widget->codec; 2298 struct soc_enum *e = 2299 (struct soc_enum *)kcontrol->private_value; 2300 int change; 2301 int ret = 0; 2302 int wi; 2303 2304 if (ucontrol->value.enumerated.item[0] >= e->max) 2305 return -EINVAL; 2306 2307 mutex_lock(&codec->mutex); 2308 2309 change = widget->value != ucontrol->value.enumerated.item[0]; 2310 if (change) { 2311 for (wi = 0; wi < wlist->num_widgets; wi++) { 2312 widget = wlist->widgets[wi]; 2313 2314 widget->value = ucontrol->value.enumerated.item[0]; 2315 2316 dapm_mux_update_power(widget, kcontrol, change, 2317 widget->value, e); 2318 } 2319 } 2320 2321 mutex_unlock(&codec->mutex); 2322 return ret; 2323 } 2324 EXPORT_SYMBOL_GPL(snd_soc_dapm_put_enum_virt); 2325 2326 /** 2327 * snd_soc_dapm_get_value_enum_double - dapm semi enumerated double mixer get 2328 * callback 2329 * @kcontrol: mixer control 2330 * @ucontrol: control element information 2331 * 2332 * Callback to get the value of a dapm semi enumerated double mixer control. 2333 * 2334 * Semi enumerated mixer: the enumerated items are referred as values. Can be 2335 * used for handling bitfield coded enumeration for example. 2336 * 2337 * Returns 0 for success. 2338 */ 2339 int snd_soc_dapm_get_value_enum_double(struct snd_kcontrol *kcontrol, 2340 struct snd_ctl_elem_value *ucontrol) 2341 { 2342 struct snd_soc_dapm_widget_list *wlist = snd_kcontrol_chip(kcontrol); 2343 struct snd_soc_dapm_widget *widget = wlist->widgets[0]; 2344 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 2345 unsigned int reg_val, val, mux; 2346 2347 reg_val = snd_soc_read(widget->codec, e->reg); 2348 val = (reg_val >> e->shift_l) & e->mask; 2349 for (mux = 0; mux < e->max; mux++) { 2350 if (val == e->values[mux]) 2351 break; 2352 } 2353 ucontrol->value.enumerated.item[0] = mux; 2354 if (e->shift_l != e->shift_r) { 2355 val = (reg_val >> e->shift_r) & e->mask; 2356 for (mux = 0; mux < e->max; mux++) { 2357 if (val == e->values[mux]) 2358 break; 2359 } 2360 ucontrol->value.enumerated.item[1] = mux; 2361 } 2362 2363 return 0; 2364 } 2365 EXPORT_SYMBOL_GPL(snd_soc_dapm_get_value_enum_double); 2366 2367 /** 2368 * snd_soc_dapm_put_value_enum_double - dapm semi enumerated double mixer set 2369 * callback 2370 * @kcontrol: mixer control 2371 * @ucontrol: control element information 2372 * 2373 * Callback to set the value of a dapm semi enumerated double mixer control. 2374 * 2375 * Semi enumerated mixer: the enumerated items are referred as values. Can be 2376 * used for handling bitfield coded enumeration for example. 2377 * 2378 * Returns 0 for success. 2379 */ 2380 int snd_soc_dapm_put_value_enum_double(struct snd_kcontrol *kcontrol, 2381 struct snd_ctl_elem_value *ucontrol) 2382 { 2383 struct snd_soc_dapm_widget_list *wlist = snd_kcontrol_chip(kcontrol); 2384 struct snd_soc_dapm_widget *widget = wlist->widgets[0]; 2385 struct snd_soc_codec *codec = widget->codec; 2386 struct soc_enum *e = (struct soc_enum *)kcontrol->private_value; 2387 unsigned int val, mux, change; 2388 unsigned int mask; 2389 struct snd_soc_dapm_update update; 2390 int wi; 2391 2392 if (ucontrol->value.enumerated.item[0] > e->max - 1) 2393 return -EINVAL; 2394 mux = ucontrol->value.enumerated.item[0]; 2395 val = e->values[ucontrol->value.enumerated.item[0]] << e->shift_l; 2396 mask = e->mask << e->shift_l; 2397 if (e->shift_l != e->shift_r) { 2398 if (ucontrol->value.enumerated.item[1] > e->max - 1) 2399 return -EINVAL; 2400 val |= e->values[ucontrol->value.enumerated.item[1]] << e->shift_r; 2401 mask |= e->mask << e->shift_r; 2402 } 2403 2404 mutex_lock(&codec->mutex); 2405 2406 change = snd_soc_test_bits(widget->codec, e->reg, mask, val); 2407 if (change) { 2408 for (wi = 0; wi < wlist->num_widgets; wi++) { 2409 widget = wlist->widgets[wi]; 2410 2411 widget->value = val; 2412 2413 update.kcontrol = kcontrol; 2414 update.widget = widget; 2415 update.reg = e->reg; 2416 update.mask = mask; 2417 update.val = val; 2418 widget->dapm->update = &update; 2419 2420 dapm_mux_update_power(widget, kcontrol, change, mux, e); 2421 2422 widget->dapm->update = NULL; 2423 } 2424 } 2425 2426 mutex_unlock(&codec->mutex); 2427 return change; 2428 } 2429 EXPORT_SYMBOL_GPL(snd_soc_dapm_put_value_enum_double); 2430 2431 /** 2432 * snd_soc_dapm_info_pin_switch - Info for a pin switch 2433 * 2434 * @kcontrol: mixer control 2435 * @uinfo: control element information 2436 * 2437 * Callback to provide information about a pin switch control. 2438 */ 2439 int snd_soc_dapm_info_pin_switch(struct snd_kcontrol *kcontrol, 2440 struct snd_ctl_elem_info *uinfo) 2441 { 2442 uinfo->type = SNDRV_CTL_ELEM_TYPE_BOOLEAN; 2443 uinfo->count = 1; 2444 uinfo->value.integer.min = 0; 2445 uinfo->value.integer.max = 1; 2446 2447 return 0; 2448 } 2449 EXPORT_SYMBOL_GPL(snd_soc_dapm_info_pin_switch); 2450 2451 /** 2452 * snd_soc_dapm_get_pin_switch - Get information for a pin switch 2453 * 2454 * @kcontrol: mixer control 2455 * @ucontrol: Value 2456 */ 2457 int snd_soc_dapm_get_pin_switch(struct snd_kcontrol *kcontrol, 2458 struct snd_ctl_elem_value *ucontrol) 2459 { 2460 struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); 2461 const char *pin = (const char *)kcontrol->private_value; 2462 2463 mutex_lock(&codec->mutex); 2464 2465 ucontrol->value.integer.value[0] = 2466 snd_soc_dapm_get_pin_status(&codec->dapm, pin); 2467 2468 mutex_unlock(&codec->mutex); 2469 2470 return 0; 2471 } 2472 EXPORT_SYMBOL_GPL(snd_soc_dapm_get_pin_switch); 2473 2474 /** 2475 * snd_soc_dapm_put_pin_switch - Set information for a pin switch 2476 * 2477 * @kcontrol: mixer control 2478 * @ucontrol: Value 2479 */ 2480 int snd_soc_dapm_put_pin_switch(struct snd_kcontrol *kcontrol, 2481 struct snd_ctl_elem_value *ucontrol) 2482 { 2483 struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); 2484 const char *pin = (const char *)kcontrol->private_value; 2485 2486 mutex_lock(&codec->mutex); 2487 2488 if (ucontrol->value.integer.value[0]) 2489 snd_soc_dapm_enable_pin(&codec->dapm, pin); 2490 else 2491 snd_soc_dapm_disable_pin(&codec->dapm, pin); 2492 2493 snd_soc_dapm_sync(&codec->dapm); 2494 2495 mutex_unlock(&codec->mutex); 2496 2497 return 0; 2498 } 2499 EXPORT_SYMBOL_GPL(snd_soc_dapm_put_pin_switch); 2500 2501 /** 2502 * snd_soc_dapm_new_control - create new dapm control 2503 * @dapm: DAPM context 2504 * @widget: widget template 2505 * 2506 * Creates a new dapm control based upon the template. 2507 * 2508 * Returns 0 for success else error. 2509 */ 2510 int snd_soc_dapm_new_control(struct snd_soc_dapm_context *dapm, 2511 const struct snd_soc_dapm_widget *widget) 2512 { 2513 struct snd_soc_dapm_widget *w; 2514 size_t name_len; 2515 2516 if ((w = dapm_cnew_widget(widget)) == NULL) 2517 return -ENOMEM; 2518 2519 name_len = strlen(widget->name) + 1; 2520 if (dapm->codec && dapm->codec->name_prefix) 2521 name_len += 1 + strlen(dapm->codec->name_prefix); 2522 w->name = kmalloc(name_len, GFP_KERNEL); 2523 if (w->name == NULL) { 2524 kfree(w); 2525 return -ENOMEM; 2526 } 2527 if (dapm->codec && dapm->codec->name_prefix) 2528 snprintf(w->name, name_len, "%s %s", 2529 dapm->codec->name_prefix, widget->name); 2530 else 2531 snprintf(w->name, name_len, "%s", widget->name); 2532 2533 dapm->n_widgets++; 2534 w->dapm = dapm; 2535 w->codec = dapm->codec; 2536 w->platform = dapm->platform; 2537 INIT_LIST_HEAD(&w->sources); 2538 INIT_LIST_HEAD(&w->sinks); 2539 INIT_LIST_HEAD(&w->list); 2540 list_add(&w->list, &dapm->card->widgets); 2541 2542 /* machine layer set ups unconnected pins and insertions */ 2543 w->connected = 1; 2544 return 0; 2545 } 2546 EXPORT_SYMBOL_GPL(snd_soc_dapm_new_control); 2547 2548 /** 2549 * snd_soc_dapm_new_controls - create new dapm controls 2550 * @dapm: DAPM context 2551 * @widget: widget array 2552 * @num: number of widgets 2553 * 2554 * Creates new DAPM controls based upon the templates. 2555 * 2556 * Returns 0 for success else error. 2557 */ 2558 int snd_soc_dapm_new_controls(struct snd_soc_dapm_context *dapm, 2559 const struct snd_soc_dapm_widget *widget, 2560 int num) 2561 { 2562 int i, ret; 2563 2564 for (i = 0; i < num; i++) { 2565 ret = snd_soc_dapm_new_control(dapm, widget); 2566 if (ret < 0) { 2567 dev_err(dapm->dev, 2568 "ASoC: Failed to create DAPM control %s: %d\n", 2569 widget->name, ret); 2570 return ret; 2571 } 2572 widget++; 2573 } 2574 return 0; 2575 } 2576 EXPORT_SYMBOL_GPL(snd_soc_dapm_new_controls); 2577 2578 static void soc_dapm_stream_event(struct snd_soc_dapm_context *dapm, 2579 const char *stream, int event) 2580 { 2581 struct snd_soc_dapm_widget *w; 2582 2583 list_for_each_entry(w, &dapm->card->widgets, list) 2584 { 2585 if (!w->sname || w->dapm != dapm) 2586 continue; 2587 dev_dbg(w->dapm->dev, "widget %s\n %s stream %s event %d\n", 2588 w->name, w->sname, stream, event); 2589 if (strstr(w->sname, stream)) { 2590 switch(event) { 2591 case SND_SOC_DAPM_STREAM_START: 2592 w->active = 1; 2593 break; 2594 case SND_SOC_DAPM_STREAM_STOP: 2595 w->active = 0; 2596 break; 2597 case SND_SOC_DAPM_STREAM_SUSPEND: 2598 case SND_SOC_DAPM_STREAM_RESUME: 2599 case SND_SOC_DAPM_STREAM_PAUSE_PUSH: 2600 case SND_SOC_DAPM_STREAM_PAUSE_RELEASE: 2601 break; 2602 } 2603 } 2604 } 2605 2606 dapm_power_widgets(dapm, event); 2607 } 2608 2609 /** 2610 * snd_soc_dapm_stream_event - send a stream event to the dapm core 2611 * @rtd: PCM runtime data 2612 * @stream: stream name 2613 * @event: stream event 2614 * 2615 * Sends a stream event to the dapm core. The core then makes any 2616 * necessary widget power changes. 2617 * 2618 * Returns 0 for success else error. 2619 */ 2620 int snd_soc_dapm_stream_event(struct snd_soc_pcm_runtime *rtd, 2621 const char *stream, int event) 2622 { 2623 struct snd_soc_codec *codec = rtd->codec; 2624 2625 if (stream == NULL) 2626 return 0; 2627 2628 mutex_lock(&codec->mutex); 2629 soc_dapm_stream_event(&codec->dapm, stream, event); 2630 mutex_unlock(&codec->mutex); 2631 return 0; 2632 } 2633 2634 /** 2635 * snd_soc_dapm_enable_pin - enable pin. 2636 * @dapm: DAPM context 2637 * @pin: pin name 2638 * 2639 * Enables input/output pin and its parents or children widgets iff there is 2640 * a valid audio route and active audio stream. 2641 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 2642 * do any widget power switching. 2643 */ 2644 int snd_soc_dapm_enable_pin(struct snd_soc_dapm_context *dapm, const char *pin) 2645 { 2646 return snd_soc_dapm_set_pin(dapm, pin, 1); 2647 } 2648 EXPORT_SYMBOL_GPL(snd_soc_dapm_enable_pin); 2649 2650 /** 2651 * snd_soc_dapm_force_enable_pin - force a pin to be enabled 2652 * @dapm: DAPM context 2653 * @pin: pin name 2654 * 2655 * Enables input/output pin regardless of any other state. This is 2656 * intended for use with microphone bias supplies used in microphone 2657 * jack detection. 2658 * 2659 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 2660 * do any widget power switching. 2661 */ 2662 int snd_soc_dapm_force_enable_pin(struct snd_soc_dapm_context *dapm, 2663 const char *pin) 2664 { 2665 struct snd_soc_dapm_widget *w = dapm_find_widget(dapm, pin, true); 2666 2667 if (!w) { 2668 dev_err(dapm->dev, "dapm: unknown pin %s\n", pin); 2669 return -EINVAL; 2670 } 2671 2672 dev_dbg(w->dapm->dev, "dapm: force enable pin %s\n", pin); 2673 w->connected = 1; 2674 w->force = 1; 2675 2676 return 0; 2677 } 2678 EXPORT_SYMBOL_GPL(snd_soc_dapm_force_enable_pin); 2679 2680 /** 2681 * snd_soc_dapm_disable_pin - disable pin. 2682 * @dapm: DAPM context 2683 * @pin: pin name 2684 * 2685 * Disables input/output pin and its parents or children widgets. 2686 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 2687 * do any widget power switching. 2688 */ 2689 int snd_soc_dapm_disable_pin(struct snd_soc_dapm_context *dapm, 2690 const char *pin) 2691 { 2692 return snd_soc_dapm_set_pin(dapm, pin, 0); 2693 } 2694 EXPORT_SYMBOL_GPL(snd_soc_dapm_disable_pin); 2695 2696 /** 2697 * snd_soc_dapm_nc_pin - permanently disable pin. 2698 * @dapm: DAPM context 2699 * @pin: pin name 2700 * 2701 * Marks the specified pin as being not connected, disabling it along 2702 * any parent or child widgets. At present this is identical to 2703 * snd_soc_dapm_disable_pin() but in future it will be extended to do 2704 * additional things such as disabling controls which only affect 2705 * paths through the pin. 2706 * 2707 * NOTE: snd_soc_dapm_sync() needs to be called after this for DAPM to 2708 * do any widget power switching. 2709 */ 2710 int snd_soc_dapm_nc_pin(struct snd_soc_dapm_context *dapm, const char *pin) 2711 { 2712 return snd_soc_dapm_set_pin(dapm, pin, 0); 2713 } 2714 EXPORT_SYMBOL_GPL(snd_soc_dapm_nc_pin); 2715 2716 /** 2717 * snd_soc_dapm_get_pin_status - get audio pin status 2718 * @dapm: DAPM context 2719 * @pin: audio signal pin endpoint (or start point) 2720 * 2721 * Get audio pin status - connected or disconnected. 2722 * 2723 * Returns 1 for connected otherwise 0. 2724 */ 2725 int snd_soc_dapm_get_pin_status(struct snd_soc_dapm_context *dapm, 2726 const char *pin) 2727 { 2728 struct snd_soc_dapm_widget *w = dapm_find_widget(dapm, pin, true); 2729 2730 if (w) 2731 return w->connected; 2732 2733 return 0; 2734 } 2735 EXPORT_SYMBOL_GPL(snd_soc_dapm_get_pin_status); 2736 2737 /** 2738 * snd_soc_dapm_ignore_suspend - ignore suspend status for DAPM endpoint 2739 * @dapm: DAPM context 2740 * @pin: audio signal pin endpoint (or start point) 2741 * 2742 * Mark the given endpoint or pin as ignoring suspend. When the 2743 * system is disabled a path between two endpoints flagged as ignoring 2744 * suspend will not be disabled. The path must already be enabled via 2745 * normal means at suspend time, it will not be turned on if it was not 2746 * already enabled. 2747 */ 2748 int snd_soc_dapm_ignore_suspend(struct snd_soc_dapm_context *dapm, 2749 const char *pin) 2750 { 2751 struct snd_soc_dapm_widget *w = dapm_find_widget(dapm, pin, false); 2752 2753 if (!w) { 2754 dev_err(dapm->dev, "dapm: unknown pin %s\n", pin); 2755 return -EINVAL; 2756 } 2757 2758 w->ignore_suspend = 1; 2759 2760 return 0; 2761 } 2762 EXPORT_SYMBOL_GPL(snd_soc_dapm_ignore_suspend); 2763 2764 /** 2765 * snd_soc_dapm_free - free dapm resources 2766 * @dapm: DAPM context 2767 * 2768 * Free all dapm widgets and resources. 2769 */ 2770 void snd_soc_dapm_free(struct snd_soc_dapm_context *dapm) 2771 { 2772 snd_soc_dapm_sys_remove(dapm->dev); 2773 dapm_debugfs_cleanup(dapm); 2774 dapm_free_widgets(dapm); 2775 list_del(&dapm->list); 2776 } 2777 EXPORT_SYMBOL_GPL(snd_soc_dapm_free); 2778 2779 static void soc_dapm_shutdown_codec(struct snd_soc_dapm_context *dapm) 2780 { 2781 struct snd_soc_dapm_widget *w; 2782 LIST_HEAD(down_list); 2783 int powerdown = 0; 2784 2785 list_for_each_entry(w, &dapm->card->widgets, list) { 2786 if (w->dapm != dapm) 2787 continue; 2788 if (w->power) { 2789 dapm_seq_insert(w, &down_list, false); 2790 w->power = 0; 2791 powerdown = 1; 2792 } 2793 } 2794 2795 /* If there were no widgets to power down we're already in 2796 * standby. 2797 */ 2798 if (powerdown) { 2799 snd_soc_dapm_set_bias_level(dapm, SND_SOC_BIAS_PREPARE); 2800 dapm_seq_run(dapm, &down_list, 0, false); 2801 snd_soc_dapm_set_bias_level(dapm, SND_SOC_BIAS_STANDBY); 2802 } 2803 } 2804 2805 /* 2806 * snd_soc_dapm_shutdown - callback for system shutdown 2807 */ 2808 void snd_soc_dapm_shutdown(struct snd_soc_card *card) 2809 { 2810 struct snd_soc_codec *codec; 2811 2812 list_for_each_entry(codec, &card->codec_dev_list, list) { 2813 soc_dapm_shutdown_codec(&codec->dapm); 2814 snd_soc_dapm_set_bias_level(&codec->dapm, SND_SOC_BIAS_OFF); 2815 } 2816 } 2817 2818 /* Module information */ 2819 MODULE_AUTHOR("Liam Girdwood, lrg@slimlogic.co.uk"); 2820 MODULE_DESCRIPTION("Dynamic Audio Power Management core for ALSA SoC"); 2821 MODULE_LICENSE("GPL"); 2822