1 /* 2 * Universal Interface for Intel High Definition Audio Codec 3 * 4 * Generic proc interface 5 * 6 * Copyright (c) 2004 Takashi Iwai <tiwai@suse.de> 7 * 8 * 9 * This driver is free software; you can redistribute it and/or modify 10 * it under the terms of the GNU General Public License as published by 11 * the Free Software Foundation; either version 2 of the License, or 12 * (at your option) any later version. 13 * 14 * This driver is distributed in the hope that it will be useful, 15 * but WITHOUT ANY WARRANTY; without even the implied warranty of 16 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 17 * GNU General Public License for more details. 18 * 19 * You should have received a copy of the GNU General Public License 20 * along with this program; if not, write to the Free Software 21 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 22 */ 23 24 #include <linux/init.h> 25 #include <linux/slab.h> 26 #include <sound/core.h> 27 #include <linux/module.h> 28 #include <sound/hda_codec.h> 29 #include "hda_local.h" 30 31 static int dump_coef = -1; 32 module_param(dump_coef, int, 0644); 33 MODULE_PARM_DESC(dump_coef, "Dump processing coefficients in codec proc file (-1=auto, 0=disable, 1=enable)"); 34 35 /* always use noncached version */ 36 #define param_read(codec, nid, parm) \ 37 snd_hdac_read_parm_uncached(&(codec)->core, nid, parm) 38 39 static const char *get_wid_type_name(unsigned int wid_value) 40 { 41 static const char * const names[16] = { 42 [AC_WID_AUD_OUT] = "Audio Output", 43 [AC_WID_AUD_IN] = "Audio Input", 44 [AC_WID_AUD_MIX] = "Audio Mixer", 45 [AC_WID_AUD_SEL] = "Audio Selector", 46 [AC_WID_PIN] = "Pin Complex", 47 [AC_WID_POWER] = "Power Widget", 48 [AC_WID_VOL_KNB] = "Volume Knob Widget", 49 [AC_WID_BEEP] = "Beep Generator Widget", 50 [AC_WID_VENDOR] = "Vendor Defined Widget", 51 }; 52 if (wid_value == -1) 53 return "UNKNOWN Widget"; 54 wid_value &= 0xf; 55 if (names[wid_value]) 56 return names[wid_value]; 57 else 58 return "UNKNOWN Widget"; 59 } 60 61 static void print_nid_array(struct snd_info_buffer *buffer, 62 struct hda_codec *codec, hda_nid_t nid, 63 struct snd_array *array) 64 { 65 int i; 66 struct hda_nid_item *items = array->list, *item; 67 struct snd_kcontrol *kctl; 68 for (i = 0; i < array->used; i++) { 69 item = &items[i]; 70 if (item->nid == nid) { 71 kctl = item->kctl; 72 snd_iprintf(buffer, 73 " Control: name=\"%s\", index=%i, device=%i\n", 74 kctl->id.name, kctl->id.index + item->index, 75 kctl->id.device); 76 if (item->flags & HDA_NID_ITEM_AMP) 77 snd_iprintf(buffer, 78 " ControlAmp: chs=%lu, dir=%s, " 79 "idx=%lu, ofs=%lu\n", 80 get_amp_channels(kctl), 81 get_amp_direction(kctl) ? "Out" : "In", 82 get_amp_index(kctl), 83 get_amp_offset(kctl)); 84 } 85 } 86 } 87 88 static void print_nid_pcms(struct snd_info_buffer *buffer, 89 struct hda_codec *codec, hda_nid_t nid) 90 { 91 int type; 92 struct hda_pcm *cpcm; 93 94 list_for_each_entry(cpcm, &codec->pcm_list_head, list) { 95 for (type = 0; type < 2; type++) { 96 if (cpcm->stream[type].nid != nid || cpcm->pcm == NULL) 97 continue; 98 snd_iprintf(buffer, " Device: name=\"%s\", " 99 "type=\"%s\", device=%i\n", 100 cpcm->name, 101 snd_hda_pcm_type_name[cpcm->pcm_type], 102 cpcm->pcm->device); 103 } 104 } 105 } 106 107 static void print_amp_caps(struct snd_info_buffer *buffer, 108 struct hda_codec *codec, hda_nid_t nid, int dir) 109 { 110 unsigned int caps; 111 caps = param_read(codec, nid, dir == HDA_OUTPUT ? 112 AC_PAR_AMP_OUT_CAP : AC_PAR_AMP_IN_CAP); 113 if (caps == -1 || caps == 0) { 114 snd_iprintf(buffer, "N/A\n"); 115 return; 116 } 117 snd_iprintf(buffer, "ofs=0x%02x, nsteps=0x%02x, stepsize=0x%02x, " 118 "mute=%x\n", 119 caps & AC_AMPCAP_OFFSET, 120 (caps & AC_AMPCAP_NUM_STEPS) >> AC_AMPCAP_NUM_STEPS_SHIFT, 121 (caps & AC_AMPCAP_STEP_SIZE) >> AC_AMPCAP_STEP_SIZE_SHIFT, 122 (caps & AC_AMPCAP_MUTE) >> AC_AMPCAP_MUTE_SHIFT); 123 } 124 125 /* is this a stereo widget or a stereo-to-mono mix? */ 126 static bool is_stereo_amps(struct hda_codec *codec, hda_nid_t nid, 127 int dir, unsigned int wcaps, int indices) 128 { 129 hda_nid_t conn; 130 131 if (wcaps & AC_WCAP_STEREO) 132 return true; 133 /* check for a stereo-to-mono mix; it must be: 134 * only a single connection, only for input, and only a mixer widget 135 */ 136 if (indices != 1 || dir != HDA_INPUT || 137 get_wcaps_type(wcaps) != AC_WID_AUD_MIX) 138 return false; 139 140 if (snd_hda_get_raw_connections(codec, nid, &conn, 1) < 0) 141 return false; 142 /* the connection source is a stereo? */ 143 wcaps = snd_hda_param_read(codec, conn, AC_PAR_AUDIO_WIDGET_CAP); 144 return !!(wcaps & AC_WCAP_STEREO); 145 } 146 147 static void print_amp_vals(struct snd_info_buffer *buffer, 148 struct hda_codec *codec, hda_nid_t nid, 149 int dir, unsigned int wcaps, int indices) 150 { 151 unsigned int val; 152 bool stereo; 153 int i; 154 155 stereo = is_stereo_amps(codec, nid, dir, wcaps, indices); 156 157 dir = dir == HDA_OUTPUT ? AC_AMP_GET_OUTPUT : AC_AMP_GET_INPUT; 158 for (i = 0; i < indices; i++) { 159 snd_iprintf(buffer, " ["); 160 val = snd_hda_codec_read(codec, nid, 0, 161 AC_VERB_GET_AMP_GAIN_MUTE, 162 AC_AMP_GET_LEFT | dir | i); 163 snd_iprintf(buffer, "0x%02x", val); 164 if (stereo) { 165 val = snd_hda_codec_read(codec, nid, 0, 166 AC_VERB_GET_AMP_GAIN_MUTE, 167 AC_AMP_GET_RIGHT | dir | i); 168 snd_iprintf(buffer, " 0x%02x", val); 169 } 170 snd_iprintf(buffer, "]"); 171 } 172 snd_iprintf(buffer, "\n"); 173 } 174 175 static void print_pcm_rates(struct snd_info_buffer *buffer, unsigned int pcm) 176 { 177 static unsigned int rates[] = { 178 8000, 11025, 16000, 22050, 32000, 44100, 48000, 88200, 179 96000, 176400, 192000, 384000 180 }; 181 int i; 182 183 pcm &= AC_SUPPCM_RATES; 184 snd_iprintf(buffer, " rates [0x%x]:", pcm); 185 for (i = 0; i < ARRAY_SIZE(rates); i++) 186 if (pcm & (1 << i)) 187 snd_iprintf(buffer, " %d", rates[i]); 188 snd_iprintf(buffer, "\n"); 189 } 190 191 static void print_pcm_bits(struct snd_info_buffer *buffer, unsigned int pcm) 192 { 193 char buf[SND_PRINT_BITS_ADVISED_BUFSIZE]; 194 195 snd_iprintf(buffer, " bits [0x%x]:", (pcm >> 16) & 0xff); 196 snd_print_pcm_bits(pcm, buf, sizeof(buf)); 197 snd_iprintf(buffer, "%s\n", buf); 198 } 199 200 static void print_pcm_formats(struct snd_info_buffer *buffer, 201 unsigned int streams) 202 { 203 snd_iprintf(buffer, " formats [0x%x]:", streams & 0xf); 204 if (streams & AC_SUPFMT_PCM) 205 snd_iprintf(buffer, " PCM"); 206 if (streams & AC_SUPFMT_FLOAT32) 207 snd_iprintf(buffer, " FLOAT"); 208 if (streams & AC_SUPFMT_AC3) 209 snd_iprintf(buffer, " AC3"); 210 snd_iprintf(buffer, "\n"); 211 } 212 213 static void print_pcm_caps(struct snd_info_buffer *buffer, 214 struct hda_codec *codec, hda_nid_t nid) 215 { 216 unsigned int pcm = param_read(codec, nid, AC_PAR_PCM); 217 unsigned int stream = param_read(codec, nid, AC_PAR_STREAM); 218 if (pcm == -1 || stream == -1) { 219 snd_iprintf(buffer, "N/A\n"); 220 return; 221 } 222 print_pcm_rates(buffer, pcm); 223 print_pcm_bits(buffer, pcm); 224 print_pcm_formats(buffer, stream); 225 } 226 227 static const char *get_jack_connection(u32 cfg) 228 { 229 static const char * const names[16] = { 230 "Unknown", "1/8", "1/4", "ATAPI", 231 "RCA", "Optical","Digital", "Analog", 232 "DIN", "XLR", "RJ11", "Comb", 233 NULL, NULL, NULL, "Other" 234 }; 235 cfg = (cfg & AC_DEFCFG_CONN_TYPE) >> AC_DEFCFG_CONN_TYPE_SHIFT; 236 if (names[cfg]) 237 return names[cfg]; 238 else 239 return "UNKNOWN"; 240 } 241 242 static const char *get_jack_color(u32 cfg) 243 { 244 static const char * const names[16] = { 245 "Unknown", "Black", "Grey", "Blue", 246 "Green", "Red", "Orange", "Yellow", 247 "Purple", "Pink", NULL, NULL, 248 NULL, NULL, "White", "Other", 249 }; 250 cfg = (cfg & AC_DEFCFG_COLOR) >> AC_DEFCFG_COLOR_SHIFT; 251 if (names[cfg]) 252 return names[cfg]; 253 else 254 return "UNKNOWN"; 255 } 256 257 /* 258 * Parse the pin default config value and returns the string of the 259 * jack location, e.g. "Rear", "Front", etc. 260 */ 261 static const char *get_jack_location(u32 cfg) 262 { 263 static const char * const bases[7] = { 264 "N/A", "Rear", "Front", "Left", "Right", "Top", "Bottom", 265 }; 266 static const unsigned char specials_idx[] = { 267 0x07, 0x08, 268 0x17, 0x18, 0x19, 269 0x37, 0x38 270 }; 271 static const char * const specials[] = { 272 "Rear Panel", "Drive Bar", 273 "Riser", "HDMI", "ATAPI", 274 "Mobile-In", "Mobile-Out" 275 }; 276 int i; 277 278 cfg = (cfg & AC_DEFCFG_LOCATION) >> AC_DEFCFG_LOCATION_SHIFT; 279 if ((cfg & 0x0f) < 7) 280 return bases[cfg & 0x0f]; 281 for (i = 0; i < ARRAY_SIZE(specials_idx); i++) { 282 if (cfg == specials_idx[i]) 283 return specials[i]; 284 } 285 return "UNKNOWN"; 286 } 287 288 /* 289 * Parse the pin default config value and returns the string of the 290 * jack connectivity, i.e. external or internal connection. 291 */ 292 static const char *get_jack_connectivity(u32 cfg) 293 { 294 static const char * const jack_locations[4] = { 295 "Ext", "Int", "Sep", "Oth" 296 }; 297 298 return jack_locations[(cfg >> (AC_DEFCFG_LOCATION_SHIFT + 4)) & 3]; 299 } 300 301 /* 302 * Parse the pin default config value and returns the string of the 303 * jack type, i.e. the purpose of the jack, such as Line-Out or CD. 304 */ 305 static const char *get_jack_type(u32 cfg) 306 { 307 static const char * const jack_types[16] = { 308 "Line Out", "Speaker", "HP Out", "CD", 309 "SPDIF Out", "Digital Out", "Modem Line", "Modem Hand", 310 "Line In", "Aux", "Mic", "Telephony", 311 "SPDIF In", "Digital In", "Reserved", "Other" 312 }; 313 314 return jack_types[(cfg & AC_DEFCFG_DEVICE) 315 >> AC_DEFCFG_DEVICE_SHIFT]; 316 } 317 318 static void print_pin_caps(struct snd_info_buffer *buffer, 319 struct hda_codec *codec, hda_nid_t nid, 320 int *supports_vref) 321 { 322 static const char * const jack_conns[4] = { 323 "Jack", "N/A", "Fixed", "Both" 324 }; 325 unsigned int caps, val; 326 327 caps = param_read(codec, nid, AC_PAR_PIN_CAP); 328 snd_iprintf(buffer, " Pincap 0x%08x:", caps); 329 if (caps & AC_PINCAP_IN) 330 snd_iprintf(buffer, " IN"); 331 if (caps & AC_PINCAP_OUT) 332 snd_iprintf(buffer, " OUT"); 333 if (caps & AC_PINCAP_HP_DRV) 334 snd_iprintf(buffer, " HP"); 335 if (caps & AC_PINCAP_EAPD) 336 snd_iprintf(buffer, " EAPD"); 337 if (caps & AC_PINCAP_PRES_DETECT) 338 snd_iprintf(buffer, " Detect"); 339 if (caps & AC_PINCAP_BALANCE) 340 snd_iprintf(buffer, " Balanced"); 341 if (caps & AC_PINCAP_HDMI) { 342 /* Realtek uses this bit as a different meaning */ 343 if ((codec->core.vendor_id >> 16) == 0x10ec) 344 snd_iprintf(buffer, " R/L"); 345 else { 346 if (caps & AC_PINCAP_HBR) 347 snd_iprintf(buffer, " HBR"); 348 snd_iprintf(buffer, " HDMI"); 349 } 350 } 351 if (caps & AC_PINCAP_DP) 352 snd_iprintf(buffer, " DP"); 353 if (caps & AC_PINCAP_TRIG_REQ) 354 snd_iprintf(buffer, " Trigger"); 355 if (caps & AC_PINCAP_IMP_SENSE) 356 snd_iprintf(buffer, " ImpSense"); 357 snd_iprintf(buffer, "\n"); 358 if (caps & AC_PINCAP_VREF) { 359 unsigned int vref = 360 (caps & AC_PINCAP_VREF) >> AC_PINCAP_VREF_SHIFT; 361 snd_iprintf(buffer, " Vref caps:"); 362 if (vref & AC_PINCAP_VREF_HIZ) 363 snd_iprintf(buffer, " HIZ"); 364 if (vref & AC_PINCAP_VREF_50) 365 snd_iprintf(buffer, " 50"); 366 if (vref & AC_PINCAP_VREF_GRD) 367 snd_iprintf(buffer, " GRD"); 368 if (vref & AC_PINCAP_VREF_80) 369 snd_iprintf(buffer, " 80"); 370 if (vref & AC_PINCAP_VREF_100) 371 snd_iprintf(buffer, " 100"); 372 snd_iprintf(buffer, "\n"); 373 *supports_vref = 1; 374 } else 375 *supports_vref = 0; 376 if (caps & AC_PINCAP_EAPD) { 377 val = snd_hda_codec_read(codec, nid, 0, 378 AC_VERB_GET_EAPD_BTLENABLE, 0); 379 snd_iprintf(buffer, " EAPD 0x%x:", val); 380 if (val & AC_EAPDBTL_BALANCED) 381 snd_iprintf(buffer, " BALANCED"); 382 if (val & AC_EAPDBTL_EAPD) 383 snd_iprintf(buffer, " EAPD"); 384 if (val & AC_EAPDBTL_LR_SWAP) 385 snd_iprintf(buffer, " R/L"); 386 snd_iprintf(buffer, "\n"); 387 } 388 caps = snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_CONFIG_DEFAULT, 0); 389 snd_iprintf(buffer, " Pin Default 0x%08x: [%s] %s at %s %s\n", caps, 390 jack_conns[(caps & AC_DEFCFG_PORT_CONN) >> AC_DEFCFG_PORT_CONN_SHIFT], 391 get_jack_type(caps), 392 get_jack_connectivity(caps), 393 get_jack_location(caps)); 394 snd_iprintf(buffer, " Conn = %s, Color = %s\n", 395 get_jack_connection(caps), 396 get_jack_color(caps)); 397 /* Default association and sequence values refer to default grouping 398 * of pin complexes and their sequence within the group. This is used 399 * for priority and resource allocation. 400 */ 401 snd_iprintf(buffer, " DefAssociation = 0x%x, Sequence = 0x%x\n", 402 (caps & AC_DEFCFG_DEF_ASSOC) >> AC_DEFCFG_ASSOC_SHIFT, 403 caps & AC_DEFCFG_SEQUENCE); 404 if (((caps & AC_DEFCFG_MISC) >> AC_DEFCFG_MISC_SHIFT) & 405 AC_DEFCFG_MISC_NO_PRESENCE) { 406 /* Miscellaneous bit indicates external hardware does not 407 * support presence detection even if the pin complex 408 * indicates it is supported. 409 */ 410 snd_iprintf(buffer, " Misc = NO_PRESENCE\n"); 411 } 412 } 413 414 static void print_pin_ctls(struct snd_info_buffer *buffer, 415 struct hda_codec *codec, hda_nid_t nid, 416 int supports_vref) 417 { 418 unsigned int pinctls; 419 420 pinctls = snd_hda_codec_read(codec, nid, 0, 421 AC_VERB_GET_PIN_WIDGET_CONTROL, 0); 422 snd_iprintf(buffer, " Pin-ctls: 0x%02x:", pinctls); 423 if (pinctls & AC_PINCTL_IN_EN) 424 snd_iprintf(buffer, " IN"); 425 if (pinctls & AC_PINCTL_OUT_EN) 426 snd_iprintf(buffer, " OUT"); 427 if (pinctls & AC_PINCTL_HP_EN) 428 snd_iprintf(buffer, " HP"); 429 if (supports_vref) { 430 int vref = pinctls & AC_PINCTL_VREFEN; 431 switch (vref) { 432 case AC_PINCTL_VREF_HIZ: 433 snd_iprintf(buffer, " VREF_HIZ"); 434 break; 435 case AC_PINCTL_VREF_50: 436 snd_iprintf(buffer, " VREF_50"); 437 break; 438 case AC_PINCTL_VREF_GRD: 439 snd_iprintf(buffer, " VREF_GRD"); 440 break; 441 case AC_PINCTL_VREF_80: 442 snd_iprintf(buffer, " VREF_80"); 443 break; 444 case AC_PINCTL_VREF_100: 445 snd_iprintf(buffer, " VREF_100"); 446 break; 447 } 448 } 449 snd_iprintf(buffer, "\n"); 450 } 451 452 static void print_vol_knob(struct snd_info_buffer *buffer, 453 struct hda_codec *codec, hda_nid_t nid) 454 { 455 unsigned int cap = param_read(codec, nid, AC_PAR_VOL_KNB_CAP); 456 snd_iprintf(buffer, " Volume-Knob: delta=%d, steps=%d, ", 457 (cap >> 7) & 1, cap & 0x7f); 458 cap = snd_hda_codec_read(codec, nid, 0, 459 AC_VERB_GET_VOLUME_KNOB_CONTROL, 0); 460 snd_iprintf(buffer, "direct=%d, val=%d\n", 461 (cap >> 7) & 1, cap & 0x7f); 462 } 463 464 static void print_audio_io(struct snd_info_buffer *buffer, 465 struct hda_codec *codec, hda_nid_t nid, 466 unsigned int wid_type) 467 { 468 int conv = snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_CONV, 0); 469 snd_iprintf(buffer, 470 " Converter: stream=%d, channel=%d\n", 471 (conv & AC_CONV_STREAM) >> AC_CONV_STREAM_SHIFT, 472 conv & AC_CONV_CHANNEL); 473 474 if (wid_type == AC_WID_AUD_IN && (conv & AC_CONV_CHANNEL) == 0) { 475 int sdi = snd_hda_codec_read(codec, nid, 0, 476 AC_VERB_GET_SDI_SELECT, 0); 477 snd_iprintf(buffer, " SDI-Select: %d\n", 478 sdi & AC_SDI_SELECT); 479 } 480 } 481 482 static void print_digital_conv(struct snd_info_buffer *buffer, 483 struct hda_codec *codec, hda_nid_t nid) 484 { 485 unsigned int digi1 = snd_hda_codec_read(codec, nid, 0, 486 AC_VERB_GET_DIGI_CONVERT_1, 0); 487 unsigned char digi2 = digi1 >> 8; 488 unsigned char digi3 = digi1 >> 16; 489 490 snd_iprintf(buffer, " Digital:"); 491 if (digi1 & AC_DIG1_ENABLE) 492 snd_iprintf(buffer, " Enabled"); 493 if (digi1 & AC_DIG1_V) 494 snd_iprintf(buffer, " Validity"); 495 if (digi1 & AC_DIG1_VCFG) 496 snd_iprintf(buffer, " ValidityCfg"); 497 if (digi1 & AC_DIG1_EMPHASIS) 498 snd_iprintf(buffer, " Preemphasis"); 499 if (digi1 & AC_DIG1_COPYRIGHT) 500 snd_iprintf(buffer, " Non-Copyright"); 501 if (digi1 & AC_DIG1_NONAUDIO) 502 snd_iprintf(buffer, " Non-Audio"); 503 if (digi1 & AC_DIG1_PROFESSIONAL) 504 snd_iprintf(buffer, " Pro"); 505 if (digi1 & AC_DIG1_LEVEL) 506 snd_iprintf(buffer, " GenLevel"); 507 if (digi3 & AC_DIG3_KAE) 508 snd_iprintf(buffer, " KAE"); 509 snd_iprintf(buffer, "\n"); 510 snd_iprintf(buffer, " Digital category: 0x%x\n", 511 digi2 & AC_DIG2_CC); 512 snd_iprintf(buffer, " IEC Coding Type: 0x%x\n", 513 digi3 & AC_DIG3_ICT); 514 } 515 516 static const char *get_pwr_state(u32 state) 517 { 518 static const char * const buf[] = { 519 "D0", "D1", "D2", "D3", "D3cold" 520 }; 521 if (state < ARRAY_SIZE(buf)) 522 return buf[state]; 523 return "UNKNOWN"; 524 } 525 526 static void print_power_state(struct snd_info_buffer *buffer, 527 struct hda_codec *codec, hda_nid_t nid) 528 { 529 static const char * const names[] = { 530 [ilog2(AC_PWRST_D0SUP)] = "D0", 531 [ilog2(AC_PWRST_D1SUP)] = "D1", 532 [ilog2(AC_PWRST_D2SUP)] = "D2", 533 [ilog2(AC_PWRST_D3SUP)] = "D3", 534 [ilog2(AC_PWRST_D3COLDSUP)] = "D3cold", 535 [ilog2(AC_PWRST_S3D3COLDSUP)] = "S3D3cold", 536 [ilog2(AC_PWRST_CLKSTOP)] = "CLKSTOP", 537 [ilog2(AC_PWRST_EPSS)] = "EPSS", 538 }; 539 540 int sup = param_read(codec, nid, AC_PAR_POWER_STATE); 541 int pwr = snd_hda_codec_read(codec, nid, 0, 542 AC_VERB_GET_POWER_STATE, 0); 543 if (sup != -1) { 544 int i; 545 546 snd_iprintf(buffer, " Power states: "); 547 for (i = 0; i < ARRAY_SIZE(names); i++) { 548 if (sup & (1U << i)) 549 snd_iprintf(buffer, " %s", names[i]); 550 } 551 snd_iprintf(buffer, "\n"); 552 } 553 554 snd_iprintf(buffer, " Power: setting=%s, actual=%s", 555 get_pwr_state(pwr & AC_PWRST_SETTING), 556 get_pwr_state((pwr & AC_PWRST_ACTUAL) >> 557 AC_PWRST_ACTUAL_SHIFT)); 558 if (pwr & AC_PWRST_ERROR) 559 snd_iprintf(buffer, ", Error"); 560 if (pwr & AC_PWRST_CLK_STOP_OK) 561 snd_iprintf(buffer, ", Clock-stop-OK"); 562 if (pwr & AC_PWRST_SETTING_RESET) 563 snd_iprintf(buffer, ", Setting-reset"); 564 snd_iprintf(buffer, "\n"); 565 } 566 567 static void print_unsol_cap(struct snd_info_buffer *buffer, 568 struct hda_codec *codec, hda_nid_t nid) 569 { 570 int unsol = snd_hda_codec_read(codec, nid, 0, 571 AC_VERB_GET_UNSOLICITED_RESPONSE, 0); 572 snd_iprintf(buffer, 573 " Unsolicited: tag=%02x, enabled=%d\n", 574 unsol & AC_UNSOL_TAG, 575 (unsol & AC_UNSOL_ENABLED) ? 1 : 0); 576 } 577 578 static inline bool can_dump_coef(struct hda_codec *codec) 579 { 580 switch (dump_coef) { 581 case 0: return false; 582 case 1: return true; 583 default: return codec->dump_coef; 584 } 585 } 586 587 static void print_proc_caps(struct snd_info_buffer *buffer, 588 struct hda_codec *codec, hda_nid_t nid) 589 { 590 unsigned int i, ncoeff, oldindex; 591 unsigned int proc_caps = param_read(codec, nid, AC_PAR_PROC_CAP); 592 ncoeff = (proc_caps & AC_PCAP_NUM_COEF) >> AC_PCAP_NUM_COEF_SHIFT; 593 snd_iprintf(buffer, " Processing caps: benign=%d, ncoeff=%d\n", 594 proc_caps & AC_PCAP_BENIGN, ncoeff); 595 596 if (!can_dump_coef(codec)) 597 return; 598 599 /* Note: This is racy - another process could run in parallel and change 600 the coef index too. */ 601 oldindex = snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_COEF_INDEX, 0); 602 for (i = 0; i < ncoeff; i++) { 603 unsigned int val; 604 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_COEF_INDEX, i); 605 val = snd_hda_codec_read(codec, nid, 0, AC_VERB_GET_PROC_COEF, 606 0); 607 snd_iprintf(buffer, " Coeff 0x%02x: 0x%04x\n", i, val); 608 } 609 snd_hda_codec_write(codec, nid, 0, AC_VERB_SET_COEF_INDEX, oldindex); 610 } 611 612 static void print_conn_list(struct snd_info_buffer *buffer, 613 struct hda_codec *codec, hda_nid_t nid, 614 unsigned int wid_type, hda_nid_t *conn, 615 int conn_len) 616 { 617 int c, curr = -1; 618 const hda_nid_t *list; 619 int cache_len; 620 621 if (conn_len > 1 && 622 wid_type != AC_WID_AUD_MIX && 623 wid_type != AC_WID_VOL_KNB && 624 wid_type != AC_WID_POWER) 625 curr = snd_hda_codec_read(codec, nid, 0, 626 AC_VERB_GET_CONNECT_SEL, 0); 627 snd_iprintf(buffer, " Connection: %d\n", conn_len); 628 if (conn_len > 0) { 629 snd_iprintf(buffer, " "); 630 for (c = 0; c < conn_len; c++) { 631 snd_iprintf(buffer, " 0x%02x", conn[c]); 632 if (c == curr) 633 snd_iprintf(buffer, "*"); 634 } 635 snd_iprintf(buffer, "\n"); 636 } 637 638 /* Get Cache connections info */ 639 cache_len = snd_hda_get_conn_list(codec, nid, &list); 640 if (cache_len >= 0 && (cache_len != conn_len || 641 memcmp(list, conn, conn_len) != 0)) { 642 snd_iprintf(buffer, " In-driver Connection: %d\n", cache_len); 643 if (cache_len > 0) { 644 snd_iprintf(buffer, " "); 645 for (c = 0; c < cache_len; c++) 646 snd_iprintf(buffer, " 0x%02x", list[c]); 647 snd_iprintf(buffer, "\n"); 648 } 649 } 650 } 651 652 static void print_gpio(struct snd_info_buffer *buffer, 653 struct hda_codec *codec, hda_nid_t nid) 654 { 655 unsigned int gpio = 656 param_read(codec, codec->core.afg, AC_PAR_GPIO_CAP); 657 unsigned int enable, direction, wake, unsol, sticky, data; 658 int i, max; 659 snd_iprintf(buffer, "GPIO: io=%d, o=%d, i=%d, " 660 "unsolicited=%d, wake=%d\n", 661 gpio & AC_GPIO_IO_COUNT, 662 (gpio & AC_GPIO_O_COUNT) >> AC_GPIO_O_COUNT_SHIFT, 663 (gpio & AC_GPIO_I_COUNT) >> AC_GPIO_I_COUNT_SHIFT, 664 (gpio & AC_GPIO_UNSOLICITED) ? 1 : 0, 665 (gpio & AC_GPIO_WAKE) ? 1 : 0); 666 max = gpio & AC_GPIO_IO_COUNT; 667 if (!max || max > 8) 668 return; 669 enable = snd_hda_codec_read(codec, nid, 0, 670 AC_VERB_GET_GPIO_MASK, 0); 671 direction = snd_hda_codec_read(codec, nid, 0, 672 AC_VERB_GET_GPIO_DIRECTION, 0); 673 wake = snd_hda_codec_read(codec, nid, 0, 674 AC_VERB_GET_GPIO_WAKE_MASK, 0); 675 unsol = snd_hda_codec_read(codec, nid, 0, 676 AC_VERB_GET_GPIO_UNSOLICITED_RSP_MASK, 0); 677 sticky = snd_hda_codec_read(codec, nid, 0, 678 AC_VERB_GET_GPIO_STICKY_MASK, 0); 679 data = snd_hda_codec_read(codec, nid, 0, 680 AC_VERB_GET_GPIO_DATA, 0); 681 for (i = 0; i < max; ++i) 682 snd_iprintf(buffer, 683 " IO[%d]: enable=%d, dir=%d, wake=%d, " 684 "sticky=%d, data=%d, unsol=%d\n", i, 685 (enable & (1<<i)) ? 1 : 0, 686 (direction & (1<<i)) ? 1 : 0, 687 (wake & (1<<i)) ? 1 : 0, 688 (sticky & (1<<i)) ? 1 : 0, 689 (data & (1<<i)) ? 1 : 0, 690 (unsol & (1<<i)) ? 1 : 0); 691 /* FIXME: add GPO and GPI pin information */ 692 print_nid_array(buffer, codec, nid, &codec->mixers); 693 print_nid_array(buffer, codec, nid, &codec->nids); 694 } 695 696 static void print_device_list(struct snd_info_buffer *buffer, 697 struct hda_codec *codec, hda_nid_t nid) 698 { 699 int i, curr = -1; 700 u8 dev_list[AC_MAX_DEV_LIST_LEN]; 701 int devlist_len; 702 703 devlist_len = snd_hda_get_devices(codec, nid, dev_list, 704 AC_MAX_DEV_LIST_LEN); 705 snd_iprintf(buffer, " Devices: %d\n", devlist_len); 706 if (devlist_len <= 0) 707 return; 708 709 curr = snd_hda_codec_read(codec, nid, 0, 710 AC_VERB_GET_DEVICE_SEL, 0); 711 712 for (i = 0; i < devlist_len; i++) { 713 if (i == curr) 714 snd_iprintf(buffer, " *"); 715 else 716 snd_iprintf(buffer, " "); 717 718 snd_iprintf(buffer, 719 "Dev %02d: PD = %d, ELDV = %d, IA = %d\n", i, 720 !!(dev_list[i] & AC_DE_PD), 721 !!(dev_list[i] & AC_DE_ELDV), 722 !!(dev_list[i] & AC_DE_IA)); 723 } 724 } 725 726 static void print_codec_core_info(struct hdac_device *codec, 727 struct snd_info_buffer *buffer) 728 { 729 snd_iprintf(buffer, "Codec: "); 730 if (codec->vendor_name && codec->chip_name) 731 snd_iprintf(buffer, "%s %s\n", 732 codec->vendor_name, codec->chip_name); 733 else 734 snd_iprintf(buffer, "Not Set\n"); 735 snd_iprintf(buffer, "Address: %d\n", codec->addr); 736 if (codec->afg) 737 snd_iprintf(buffer, "AFG Function Id: 0x%x (unsol %u)\n", 738 codec->afg_function_id, codec->afg_unsol); 739 if (codec->mfg) 740 snd_iprintf(buffer, "MFG Function Id: 0x%x (unsol %u)\n", 741 codec->mfg_function_id, codec->mfg_unsol); 742 snd_iprintf(buffer, "Vendor Id: 0x%08x\n", codec->vendor_id); 743 snd_iprintf(buffer, "Subsystem Id: 0x%08x\n", codec->subsystem_id); 744 snd_iprintf(buffer, "Revision Id: 0x%x\n", codec->revision_id); 745 746 if (codec->mfg) 747 snd_iprintf(buffer, "Modem Function Group: 0x%x\n", codec->mfg); 748 else 749 snd_iprintf(buffer, "No Modem Function Group found\n"); 750 } 751 752 static void print_codec_info(struct snd_info_entry *entry, 753 struct snd_info_buffer *buffer) 754 { 755 struct hda_codec *codec = entry->private_data; 756 hda_nid_t nid, fg; 757 int i, nodes; 758 759 print_codec_core_info(&codec->core, buffer); 760 fg = codec->core.afg; 761 if (!fg) 762 return; 763 snd_hda_power_up(codec); 764 snd_iprintf(buffer, "Default PCM:\n"); 765 print_pcm_caps(buffer, codec, fg); 766 snd_iprintf(buffer, "Default Amp-In caps: "); 767 print_amp_caps(buffer, codec, fg, HDA_INPUT); 768 snd_iprintf(buffer, "Default Amp-Out caps: "); 769 print_amp_caps(buffer, codec, fg, HDA_OUTPUT); 770 snd_iprintf(buffer, "State of AFG node 0x%02x:\n", fg); 771 print_power_state(buffer, codec, fg); 772 773 nodes = snd_hda_get_sub_nodes(codec, fg, &nid); 774 if (! nid || nodes < 0) { 775 snd_iprintf(buffer, "Invalid AFG subtree\n"); 776 snd_hda_power_down(codec); 777 return; 778 } 779 780 print_gpio(buffer, codec, fg); 781 if (codec->proc_widget_hook) 782 codec->proc_widget_hook(buffer, codec, fg); 783 784 for (i = 0; i < nodes; i++, nid++) { 785 unsigned int wid_caps = 786 param_read(codec, nid, AC_PAR_AUDIO_WIDGET_CAP); 787 unsigned int wid_type = get_wcaps_type(wid_caps); 788 hda_nid_t *conn = NULL; 789 int conn_len = 0; 790 791 snd_iprintf(buffer, "Node 0x%02x [%s] wcaps 0x%x:", nid, 792 get_wid_type_name(wid_type), wid_caps); 793 if (wid_caps & AC_WCAP_STEREO) { 794 unsigned int chans = get_wcaps_channels(wid_caps); 795 if (chans == 2) 796 snd_iprintf(buffer, " Stereo"); 797 else 798 snd_iprintf(buffer, " %d-Channels", chans); 799 } else 800 snd_iprintf(buffer, " Mono"); 801 if (wid_caps & AC_WCAP_DIGITAL) 802 snd_iprintf(buffer, " Digital"); 803 if (wid_caps & AC_WCAP_IN_AMP) 804 snd_iprintf(buffer, " Amp-In"); 805 if (wid_caps & AC_WCAP_OUT_AMP) 806 snd_iprintf(buffer, " Amp-Out"); 807 if (wid_caps & AC_WCAP_STRIPE) 808 snd_iprintf(buffer, " Stripe"); 809 if (wid_caps & AC_WCAP_LR_SWAP) 810 snd_iprintf(buffer, " R/L"); 811 if (wid_caps & AC_WCAP_CP_CAPS) 812 snd_iprintf(buffer, " CP"); 813 snd_iprintf(buffer, "\n"); 814 815 print_nid_array(buffer, codec, nid, &codec->mixers); 816 print_nid_array(buffer, codec, nid, &codec->nids); 817 print_nid_pcms(buffer, codec, nid); 818 819 /* volume knob is a special widget that always have connection 820 * list 821 */ 822 if (wid_type == AC_WID_VOL_KNB) 823 wid_caps |= AC_WCAP_CONN_LIST; 824 825 if (wid_caps & AC_WCAP_CONN_LIST) { 826 conn_len = snd_hda_get_num_raw_conns(codec, nid); 827 if (conn_len > 0) { 828 conn = kmalloc_array(conn_len, 829 sizeof(hda_nid_t), 830 GFP_KERNEL); 831 if (!conn) 832 return; 833 if (snd_hda_get_raw_connections(codec, nid, conn, 834 conn_len) < 0) 835 conn_len = 0; 836 } 837 } 838 839 if (wid_caps & AC_WCAP_IN_AMP) { 840 snd_iprintf(buffer, " Amp-In caps: "); 841 print_amp_caps(buffer, codec, nid, HDA_INPUT); 842 snd_iprintf(buffer, " Amp-In vals: "); 843 if (wid_type == AC_WID_PIN || 844 (codec->single_adc_amp && 845 wid_type == AC_WID_AUD_IN)) 846 print_amp_vals(buffer, codec, nid, HDA_INPUT, 847 wid_caps, 1); 848 else 849 print_amp_vals(buffer, codec, nid, HDA_INPUT, 850 wid_caps, conn_len); 851 } 852 if (wid_caps & AC_WCAP_OUT_AMP) { 853 snd_iprintf(buffer, " Amp-Out caps: "); 854 print_amp_caps(buffer, codec, nid, HDA_OUTPUT); 855 snd_iprintf(buffer, " Amp-Out vals: "); 856 if (wid_type == AC_WID_PIN && 857 codec->pin_amp_workaround) 858 print_amp_vals(buffer, codec, nid, HDA_OUTPUT, 859 wid_caps, conn_len); 860 else 861 print_amp_vals(buffer, codec, nid, HDA_OUTPUT, 862 wid_caps, 1); 863 } 864 865 switch (wid_type) { 866 case AC_WID_PIN: { 867 int supports_vref; 868 print_pin_caps(buffer, codec, nid, &supports_vref); 869 print_pin_ctls(buffer, codec, nid, supports_vref); 870 break; 871 } 872 case AC_WID_VOL_KNB: 873 print_vol_knob(buffer, codec, nid); 874 break; 875 case AC_WID_AUD_OUT: 876 case AC_WID_AUD_IN: 877 print_audio_io(buffer, codec, nid, wid_type); 878 if (wid_caps & AC_WCAP_DIGITAL) 879 print_digital_conv(buffer, codec, nid); 880 if (wid_caps & AC_WCAP_FORMAT_OVRD) { 881 snd_iprintf(buffer, " PCM:\n"); 882 print_pcm_caps(buffer, codec, nid); 883 } 884 break; 885 } 886 887 if (wid_caps & AC_WCAP_UNSOL_CAP) 888 print_unsol_cap(buffer, codec, nid); 889 890 if (wid_caps & AC_WCAP_POWER) 891 print_power_state(buffer, codec, nid); 892 893 if (wid_caps & AC_WCAP_DELAY) 894 snd_iprintf(buffer, " Delay: %d samples\n", 895 (wid_caps & AC_WCAP_DELAY) >> 896 AC_WCAP_DELAY_SHIFT); 897 898 if (wid_type == AC_WID_PIN && codec->dp_mst) 899 print_device_list(buffer, codec, nid); 900 901 if (wid_caps & AC_WCAP_CONN_LIST) 902 print_conn_list(buffer, codec, nid, wid_type, 903 conn, conn_len); 904 905 if (wid_caps & AC_WCAP_PROC_WID) 906 print_proc_caps(buffer, codec, nid); 907 908 if (codec->proc_widget_hook) 909 codec->proc_widget_hook(buffer, codec, nid); 910 911 kfree(conn); 912 } 913 snd_hda_power_down(codec); 914 } 915 916 /* 917 * create a proc read 918 */ 919 int snd_hda_codec_proc_new(struct hda_codec *codec) 920 { 921 char name[32]; 922 struct snd_info_entry *entry; 923 int err; 924 925 snprintf(name, sizeof(name), "codec#%d", codec->core.addr); 926 err = snd_card_proc_new(codec->card, name, &entry); 927 if (err < 0) 928 return err; 929 930 snd_info_set_text_ops(entry, codec, print_codec_info); 931 return 0; 932 } 933 934