clawdie-iso/live/operator-session/clawdie-live-audio

74 lines
2 KiB
Text
Raw Permalink Normal View History

#!/bin/sh
# Clawdie operator USB audio default selector.
#
# Laptops with HDMI attached can expose the GPU HDMI codec as pcm0, making
# FreeBSD choose HDMI as hw.snd.default_unit even when the internal speaker is
# available. Prefer an internal analog-style playback device when one exists;
# leave the system untouched if no better candidate can be identified.
# PROVIDE: clawdie_live_audio
# REQUIRE: FILESYSTEMS kld
# BEFORE: sddm
# KEYWORD: nojail
. /etc/rc.subr
name="clawdie_live_audio"
rcvar="${name}_enable"
start_cmd="${name}_start"
stop_cmd=":"
clawdie_live_audio_pick_unit() {
[ -r /dev/sndstat ] || return 1
awk '
/^pcm[0-9]+:/ {
unit = $1
sub(/^pcm/, "", unit)
sub(/:$/, "", unit)
line = tolower($0)
score = 0
if (line ~ /hdmi|displayport/) score -= 100
if (line ~ /realtek|analog|speaker|headphone|alc/) score += 80
if (line ~ /play/) score += 10
if (line ~ /default/) score += 1
if (best == "" || score > best_score) {
best = unit
best_score = score
best_line = $0
}
}
END {
if (best != "" && best_score > -100) {
print best
}
}
' /dev/sndstat
}
clawdie_live_audio_start() {
_unit="$(clawdie_live_audio_pick_unit 2>/dev/null || true)"
if [ -z "${_unit:-}" ]; then
echo "${name}: no non-HDMI playback device selected"
return 0
fi
_current="$(sysctl -n hw.snd.default_unit 2>/dev/null || true)"
if [ "${_current}" = "${_unit}" ]; then
echo "${name}: hw.snd.default_unit already ${_unit}"
return 0
fi
if sysctl "hw.snd.default_unit=${_unit}" >/dev/null 2>&1; then
echo "${name}: set hw.snd.default_unit=${_unit}"
else
echo "${name}: failed to set hw.snd.default_unit=${_unit}" >&2
return 1
fi
}
load_rc_config "$name"
: "${clawdie_live_audio_enable:=YES}"
run_rc_command "$1"