| #!/bin/sh |
| # |
| # Copyright (c) 2013 The Chromium OS Authors. All rights reserved. |
| # Use of this source code is governed by a BSD-style license that can be |
| # found in the LICENSE file. |
| # |
| # Collect information about the audio system from top to bottom. |
| |
| dump_cards() { |
| # shellcheck disable=SC2068 |
| for card in ${@} |
| do |
| echo "=== amixer -c ${card} scontents ===" |
| amixer -c "${card}" scontents |
| echo "=== amixer -c ${card} contents ===" |
| amixer -c "${card}" contents |
| done |
| } |
| |
| # Helper function: in_the_list $1 $2 |
| # Returns 0 if str $1 is included in delimited str $2; otherwise 1 |
| in_the_list() { |
| for item in $2 |
| do |
| if [ "$1" = "${item}" ]; then |
| return 0 |
| fi |
| done |
| return 1 |
| } |
| |
| echo '=== cras_test_client --dump_server_info ===' |
| cras_test_client --dump_server_info |
| |
| echo '=== cras_test_client --dump_audio_thread ===' |
| cras_test_client --dump_audio_thread |
| |
| echo '=== cras_test_client --dump_main ===' |
| cras_test_client --dump_main |
| |
| echo '=== cras_test_client --dump_bt ===' |
| cras_test_client --dump_bt |
| |
| echo '=== cras_test_client --dump_events ===' |
| cras_test_client --dump_events |
| |
| echo '=== aplay -l ===' |
| aplay -l |
| echo '=== arecord -l ===' |
| arecord -l |
| |
| output_cards=$( |
| aplay -l | grep -E ^card | sed 's/card \([0-9]\+\).*/\1/' | sort -u) |
| dump_cards "${output_cards}" |
| |
| input_cards=$( |
| arecord -l | grep -E ^card | sed 's/card \([0-9]\+\).*/\1/' | sort -u) |
| dump_cards "${input_cards}" |
| |
| # HDA codec for codecs on x86. |
| codecs=$(find /proc/asound -mindepth 2 -maxdepth 2 -path '*card*/codec#*') |
| for codec in ${codecs} |
| do |
| echo "=== codec: ${codec} ===" |
| cat "${codec}" |
| done |
| |
| # I2C dump for codecs on arm. |
| # Find lines like "max98088.7-0010" and extract "7 0x0010" from it. |
| if [ -e /sys/kernel/debug/asoc/codecs ]; then |
| sed_expr='s/^\([^.-]\+\)\.\([0-9]\+\)-\([0-9]\+\)$/\2 0x\3/p' |
| sed -n "${sed_expr}" /sys/kernel/debug/asoc/codecs | |
| while read -r i2c_addr |
| do |
| echo "=== i2cdump -f -y ${i2c_addr} ===" |
| i2cdump -f -y "${i2c_addr}" |
| done |
| fi |
| |
| # Dump registers from regmaps |
| |
| # List of audio components |
| # For kernel>=4.14, it is in /sys/kernel/debug/asoc/components |
| # For kernel<4.14, it is in /sys/kernel/debug/asoc/codecs |
| if [ -f /sys/kernel/debug/asoc/components ]; then |
| audio_comps=$(cat /sys/kernel/debug/asoc/components) |
| else |
| audio_comps=$(cat /sys/kernel/debug/asoc/codecs) |
| fi |
| |
| # Blocklist regmap name of dumping registers (tracked by b/154177454) |
| # Use the blank space as delimiter, e.g. 'name_a name_b name_c' |
| name_blocklist='snd_hda_codec_hdmi' |
| |
| for file_path in /sys/kernel/debug/regmap/* |
| do |
| [ -e "${file_path}" ] || break # handle the case of no files |
| component=$(basename "${file_path}") |
| |
| # Skip dumping registers if component is not listed in audio_comps |
| if ! in_the_list "${component}" "${audio_comps}"; then |
| continue |
| fi |
| |
| if [ ! -f "${file_path}/name" ]; then |
| echo "Failed at dump registers: ${file_path}" |
| continue |
| fi |
| |
| name=$(cat "${file_path}/name") |
| echo "=== dump registers component: ${component} name: ${name} ===" |
| |
| # Skip dumping registers if regmap's name is in name_blocklist |
| if in_the_list "${name}" "${name_blocklist}"; then |
| echo 'skipped dumping due to b/154177454' |
| continue |
| fi |
| |
| # Store back the original value |
| # Note: $(cat cache_bypass) returns 'Y' if flag is on; otherwise 'N' |
| cache_bypass=$(cat "${file_path}/cache_bypass") |
| if [ "${cache_bypass}" = "N" ]; then |
| echo 1 > "${file_path}/cache_bypass" |
| fi |
| cat "${file_path}/registers" |
| if [ "${cache_bypass}" = "N" ]; then |
| echo 0 > "${file_path}/cache_bypass" |
| fi |
| done |