diff --git a/case-lib/lib.sh b/case-lib/lib.sh index 5cb486bc..2ee34338 100644 --- a/case-lib/lib.sh +++ b/case-lib/lib.sh @@ -828,7 +828,7 @@ set_sof_volume() tinymix -D"$device" set "$control_name" "$value" ;; *) - die "Unknown alsa tool $SOF_ALSA_TOOL" + die "Unknown ALSA tool ${SOF_ALSA_TOOL}" ;; esac } @@ -847,7 +847,7 @@ get_sof_controls() tinymix --card "$sofcard" controls ;; *) - die "Unknown alsa tool $SOF_ALSA_TOOL" + die "Unknown ALSA tool ${SOF_ALSA_TOOL}" ;; esac } @@ -863,7 +863,7 @@ kill_play_record() pkill -9 tinyplay ;; *) - die "Unknown alsa tool $SOF_ALSA_TOOL" + die "Unknown ALSA tool ${SOF_ALSA_TOOL}" ;; esac } @@ -888,7 +888,7 @@ check_alsa_tool_process() die "tinyplay process is terminated too early" ;; *) - die "Unknown alsa tool $SOF_ALSA_TOOL" + die "Unknown ALSA tool ${SOF_ALSA_TOOL}" ;; esac } @@ -911,7 +911,7 @@ aplay_opts() # shellcheck disable=SC2086 aplay $SOF_ALSA_OPTS $SOF_APLAY_OPTS "$@" else - die "Unknown ALSA tool: $SOF_ALSA_TOOL" + die "Unknown ALSA tool: ${SOF_ALSA_TOOL}" fi } @@ -930,7 +930,7 @@ arecord_opts() # shellcheck disable=SC2086 arecord $SOF_ALSA_OPTS $SOF_ARECORD_OPTS "$@" else - die "Unknown ALSA tool: $SOF_ALSA_TOOL" + die "Unknown ALSA tool: ${SOF_ALSA_TOOL}" fi } @@ -1236,16 +1236,72 @@ reset_sof_volume() get_sof_controls "0" | sed -e "s/^.*'\(.*\)'.*/\1/" |grep -E 'PGA|gain' | while read -r mixer_name do + dlogi "Reset volume to ${level_db} on ${mixer_name}" if [[ "$SOF_ALSA_TOOL" = "alsa" ]]; then amixer -Dhw:0 -- sset "$mixer_name" "$level_db" - elif [[ "$SOF_ALSA_TOOL" = "tinyalsa" ]]; then + elif [[ "$SOF_ALSA_TOOL" = "tinyalsa" ]]; then tinymix -D0 set "$mixer_name" "$level_db" else - echo "Unknown alsa tool $SOF_ALSA_TOOL" - break + die "Unknown ALSA tool ${SOF_ALSA_TOOL}" fi done } + +# Initialize and restore ALSA mixer state to the last saved on the DUT, +# reset volume, and apply the HW MODEL-specific settings, if defined. +# +# This initialization procedure assumes that the DUT's ALSA init files, +# UCM2, and default state (/var/lib/alsa/asound.state) are either kept +# unchanged as a 'golden' config, or _mostly_ consistent with the MODEL. +# The latter case is when the alsa-restore service is active on the DUT and +# the state file keeps the last active mixer settings persistent to restore +# them after the DUT's reboot. +# The init files and the persistent state file should diverge not more +# than set_alsa_settings() aligns and should be reset to a 'golden' config +# during the DUT's deployment step of the test plan execution, +# which is external to the test case scope of operations. +# +set_alsa() +{ + local alsa_log="${LOG_ROOT}/alsa_setup.log" + local asound_state="${LOG_ROOT}/asound_state" + local rc=0 + + # Read the ALSA restore service status + systemctl --no-pager status alsa-restore.service > "${alsa_log}" 2>&1 || rc=$? + [[ "${rc}" -ne 0 ]] && dlogw "alsa-restore check error=${rc}" && rc=0 + [ -f /lib/systemd/system/alsa-restore.service ] && cat /lib/systemd/system/alsa-restore.service >> "${alsa_log}" + + alsactl store -f "${asound_state}_old.txt" 2>&1 || rc=$? + [[ "${rc}" -ne 0 ]] && dlogw "alsactl store error=${rc}" && rc=0 + + dlogi "Try to initialize all devices to their default ALSA state (alsactl init)." + printf '%s\n' '-vv------- ALSA init -------vv-' >> "${alsa_log}" + alsactl -d init >> "${alsa_log}" 2>&1 || rc=$? + [[ "${rc}" -ne 0 ]] && dlogw "alsactl init error=${rc}" && rc=0 + printf '%s\n' '-^^------- ALSA init -------^^-' >> "${alsa_log}" + + dlogi "Restore ALSA defaults from /var/lib/alsa/asound.state" + printf '%s\n' '-vv------- Restore ALSA defaults -------vv-' >> "${alsa_log}" + # We don't need in sudo to write our log file, but to call `alsactl` + # shellcheck disable=SC2024 + sudo alsactl -d restore >> "${alsa_log}" 2>&1 || rc=$? + [[ "${rc}" -ne 0 ]] && dlogw "alsactl restore error=${rc}" && rc=0 + printf '%s\n' '-^^------- Restore ALSA defaults -------^^-' >> "${alsa_log}" + + reset_sof_volume + + # If MODEL is defined, set proper gain for the platform + if [ -z "$MODEL" ]; then + dlogw "NO MODEL is defined. Please define MODEL to run alsa_settings/\${MODEL}.sh" + else + set_alsa_settings "$MODEL" + fi + + alsactl store -f "${asound_state}.txt" 2>&1 || rc=$? + [[ "${rc}" -ne 0 ]] && dlogw "alsactl store error=${rc}" +} + DO_PERF_ANALYSIS=0 perf_analyze() diff --git a/test-case/check-alsa-conformance.sh b/test-case/check-alsa-conformance.sh index e71cdfe9..5899944c 100755 --- a/test-case/check-alsa-conformance.sh +++ b/test-case/check-alsa-conformance.sh @@ -221,18 +221,6 @@ select_PCMs() done dlogi "Capture devices: ${CAPTURE_DEVICES[*]}" } - -set_alsa() -{ - reset_sof_volume - - # If MODEL is defined, set proper gain for the platform - if [ -z "$MODEL" ]; then - dlogw "No MODEL is defined. Please define MODEL to run alsa_settings/\${MODEL}.sh" - else - set_alsa_settings "$MODEL" - fi -} alsa_conformance_device_info() { diff --git a/test-case/check-alsabat.sh b/test-case/check-alsabat.sh index 9aadb863..644648ff 100755 --- a/test-case/check-alsabat.sh +++ b/test-case/check-alsabat.sh @@ -83,20 +83,10 @@ fi check_locale_for_alsabat -# reset sof volume to 0dB -reset_sof_volume - -# If MODEL is defined, set proper gain for the platform -if [ -z "$MODEL" ]; then - # treat as warning only - dlogw "NO MODEL is defined. Please define MODEL to run alsa_settings/MODEL.sh" -else - #dlogi "apply alsa settings for alsa_settings/MODEL.sh" - set_alsa_settings "$MODEL" -fi - logger_disabled || func_lib_start_log_collect +set_alsa + function __upload_wav_file { # upload the alsabat wav file @@ -112,13 +102,13 @@ function __upload_wav_file # check the PCMs before alsabat test dlogi "check the PCMs before alsabat test" -aplay -Dplug$pcm_p -d 1 /dev/zero -q || die "Failed to play on PCM: $pcm_p" -arecord -Dplug$pcm_c -d 1 /dev/null -q || die "Failed to capture on PCM: $pcm_c" +aplay "-Dplug${pcm_p}" -d 1 /dev/zero -q || die "Failed to play on PCM: ${pcm_p}" +arecord "-Dplug${pcm_c}" -d 1 /dev/null -q || die "Failed to capture on PCM: ${pcm_c}" # alsabat test # BT offload PCMs also support mono playback. dlogc "alsabat -P$pcm_p --standalone -n $frames -r $rate -c $channel_p -f $format -F $frequency -k $sigmak" -alsabat -P$pcm_p --standalone -n $frames -c $channel_p -r $rate -f $format -F $frequency -k $sigmak & playPID=$! +alsabat "-P${pcm_p}" --standalone -n "${frames}" -c "${channel_p}" -r "${rate}" -f "${format}" -F "${frequency}" -k "${sigmak}" & playPID=$! # playback may have low latency, add one second delay to aviod recording zero at beginning. sleep 1 @@ -132,7 +122,7 @@ amixer -c "${first_card_name}" contents > "$LOG_ROOT"/amixer_settings.txt # We use different USB sound cards in CI, part of them only support 1 channel for capture, # so make the channel as an option and config it in alsabat-playback.csv dlogc "alsabat -C$pcm_c -c $channel_c -r $rate -f $format -F $frequency -k $sigmak" -alsabat -C$pcm_c -c $channel_c -r $rate -f $format -F $frequency -k $sigmak || { +alsabat "-C${pcm_c}" -c "${channel_c}" -r "${rate}" -f "${format}" -F "${frequency}" -k "${sigmak}" || { # upload failed wav file __upload_wav_file exit 1 diff --git a/test-case/latency-metrics.sh b/test-case/latency-metrics.sh index c8c6bd0c..9ad07f25 100755 --- a/test-case/latency-metrics.sh +++ b/test-case/latency-metrics.sh @@ -142,18 +142,6 @@ check_latency_options() fi } -set_alsa() -{ - reset_sof_volume - - # If MODEL is defined, set proper gain for the platform - if [ -z "$MODEL" ]; then - dlogw "NO MODEL is defined. Please define MODEL to run alsa_settings/MODEL.sh" - else - set_alsa_settings "$MODEL" - fi -} - # set/update commands in case the test iterates or sweep over a range compose_commands() {