Управление вентилятором Radeon RX-6xx0: различия между версиями

Материал из ALT Linux Wiki
Строка 101: Строка 101:
#Пользовательскими переменными задаю:
#Пользовательскими переменными задаю:
#:*№ видюхи (если есть встройка, она, вероятно, будет пронумерована единичкой);
#:*№ видюхи (если есть встройка, она, вероятно, будет пронумерована единичкой);
#:*частоту опроса температуры '''rate''' со сменой состояния ШИМ-контроллера при необходимости (5 секунд хватает и чтоб не дать перегреться, и чтоб не надоело листать портянку журнала);
#:*частоту опроса температуры '''rate''' со сменой значения в ШИМ-контроллере при необходимости (5 секунд хватает и чтоб не дать перегреться, и чтоб не надоело листать портянку журнала);
#:*температуру '''min_tmp''', ниже которой мослать вентилятором бессмысленно (с завода вентилятор не алё градусов до полусотни минимум, что видно в логе при перезапуске этого скрипта в жару — ШИМ на нуле после автонастртойки);
#:*температуру '''min_tmp''', ниже которой мослать вентилятором бессмысленно (с завода вентилятор не алё градусов до полусотни минимум, что видно в логе при перезапуске скрипта);
#:*шаг '''gap_tmp''' между диапазонами температур (20 градусов).
#:*шаг '''gap_tmp''' между диапазонами температур (20 градусов).
#В выборке '''case''' цикла '''for''' указываю, насколько разгоняться — сиречь, какие значения выставлять ШИМ-контроллеру в этих температурных диапазонах (задаются не об/мин, как можно подумать, а нечто вроде процента от максимума — но не из 100, а из 255).
#В выборке '''case''' цикла '''for''' указываю, насколько разгоняться — сиречь, какие значения выставлять ШИМу в этих температурных диапазонах (задаются не об/мин, как можно подумать, а нечто вроде процента от максимума — но не из 100, а из 255).
#Значение ШИМ практически никогда не сохраняется в назначенном виде — постоянно на единичку-другую ниже, чем и обусловлено сличение нового значения с текущим тоже в некотором диапазоне.
#Значение ШИМ практически никогда не сохраняется в назначенном виде — постоянно гуляет туда-сюда, чем и обусловлено сличение нового значения с текущим тоже в некотором диапазоне.
#Сделал скрипт а-ля «резидентным» (цикл '''while'''), запускать по таймеру не стал, дабы между его запусками не оставлять видюху в ручном режиме без управления (см. функцию '''fanmode''').
#Сделал скрипт а-ля «резидентным» (цикл '''while''') запускать по таймеру не стал, дабы между его запусками не оставлять видюху в ручном режиме без управления (см. функцию '''fanmode''').


==Запускающий юнит==
==Запускающий юнит==

Версия от 09:50, 25 мая 2022

Введение

Столкнулся с проблемой перегрева видюхи RX-6700XT на игровых нагрузках — и не только её самой, поскольку она ведь и вокруг себя знатно греет.

  • Процессор прямо над нею кипятится — места в простенке между видюхой, крышкой и стенками отнюдь не завались.
  • М2-накопитель между видюхой и процом тоже знатно подгорает, хоть и с радиатором, и от проц-кулера на него дует... горячим. :)
  • Дополнительные винчестеры в корзине, вставленной в пространство 5-дюймовых отсеков.
  • Да и тем, что в нижних 3,5-дюймовых отсеках, ни разу не уютно.

В некоторой степени спасает вариант поставить (скорей, положить) перед открытой крышкой системника большой комнатный вентилятор — для всего, кроме самой видюхи: она ж к нему краем, и толку ноль. А заводская авторегулировка видюхиного ШИМа как-то не особо способствует её охлаждению даже зимой, о жаре за бортом вовсе молчу.

Реализация

Вдохновлённый решением одного немца amdgpu-fancontrol, сваял собственный сильно упрощённый вариант.

Понадобится создать пару файлов.

Скрипт запуска

/usr/local/sbin/amdgpufan:

#!/bin/bash
# Check root privileges first.
[ $UID -eq 0 ] || {
    echo "Writing to /sys requires root privileges."
    exit 1
}
    
## User variables #############################################
card=0
rate=5
min_tmp=40
gap_tmp=$[min_tmp/2]
## System variables ###########################################
sys_dir=`ls -d /sys/class/drm/card$card/device/hwmon/*`
## temp# - 1:edge, 2:junction, 3:memory
sys_tmp=${sys_dir}/temp2_input
sys_pwm=${sys_dir}/pwm1
sys_fan=${sys_pwm}_enable

min_pwm=`cat ${sys_pwm}_min`
max_pwm=`cat ${sys_pwm}_max`
max_tmp=$[`cat ${sys_dir}/temp*_crit | sort -V | head -1`/1000]
###############################################################

reset(){
    printf "Exiting and setting fan mode"
    fanmode auto
    exit 0
}

fanmode(){
    case $1 in
        manual) mode=1;;
        auto)   mode=2;;
        *)      mode=0 # max
    esac
    echo " to '$1'."
    echo $mode >$sys_fan
}

main(){
    cur_pwm=`cat $sys_pwm`
    cur_tmp=$[`cat $sys_tmp`/1000]
    [[ `cat $sys_fan` -eq 1 ]] || {
        printf "Wrong fan mode, setting"
        fanmode manual
    }
    if  [[ $cur_tmp -ge $max_tmp ]]; then
        echo "$cur_tmp°C above critical, setting PWM to $max_pwm for max speed."
        new_pwm=$max_pwm
    else
        [[ $cur_tmp -le $min_tmp ]] && new_pwm=$min_pwm || {
            for n in `seq 0 3`; do
                case $n in
                    0) add=70;;
                    1) add=90;;
                    2) add=140;;
                    3) add=210;;
                esac
                [[ $cur_tmp -ge $[min_tmp+gap_tmp*n]     ]] &&
                [[ $cur_tmp -le $[min_tmp+gap_tmp*(n+1)] ]] && {
                    new_pwm=$[min_pwm+add]
                    break
                }
            done
        }
    fi
    printf "%3d°C @%3d PWM" $cur_tmp $cur_pwm
    [[ $cur_pwm -ge $[new_pwm-2] ]] &&
    [[ $cur_pwm -le  $new_pwm    ]] &&
    echo "." || { # Change PWM if differ.
        printf ", changing to %3d.\n" $new_pwm
        echo $new_pwm >$sys_pwm
    }
}

trap "reset" SIGINT SIGTERM # Handle signals.

while :; do # run daemon
    main
    sleep ${rate}s
done

Пояснения

  1. В системных переменных отслеживаю показания датчика самого горячего элемента из трёх — junction (sys_tmp), но в качестве предельной температуры (max_tmp) выбираю минимальную из критических (в моём случае это датчик памяти).
  2. Пользовательскими переменными задаю:
    • № видюхи (если есть встройка, она, вероятно, будет пронумерована единичкой);
    • частоту опроса температуры rate со сменой значения в ШИМ-контроллере при необходимости (5 секунд хватает и чтоб не дать перегреться, и чтоб не надоело листать портянку журнала);
    • температуру min_tmp, ниже которой мослать вентилятором бессмысленно (с завода вентилятор не алё градусов до полусотни минимум, что видно в логе при перезапуске скрипта);
    • шаг gap_tmp между диапазонами температур (20 градусов).
  3. В выборке case цикла for указываю, насколько разгоняться — сиречь, какие значения выставлять ШИМу в этих температурных диапазонах (задаются не об/мин, как можно подумать, а нечто вроде процента от максимума — но не из 100, а из 255).
  4. Значение ШИМ практически никогда не сохраняется в назначенном виде — постоянно гуляет туда-сюда, чем и обусловлено сличение нового значения с текущим тоже в некотором диапазоне.
  5. Сделал скрипт а-ля «резидентным» (цикл while) — запускать по таймеру не стал, дабы между его запусками не оставлять видюху в ручном режиме без управления (см. функцию fanmode).

Запускающий юнит

/lib/systemd/system/amdgpufan.service:

[Unit]
Description = AMD GPU fan control

[Service]
ExecStart = /usr/local/sbin/amdgpufan
Restart = on-failure
RestartSec = 5

[Install]
WantedBy = default.target

Пример работы

(дату-время и имя-пид процесса убрал для удобочитаемости)

Вечер — веб-сёрфинг, редактирование и пр. Колебания Т°C на ШИМ 69:

 54°C @ 69 PWM.

Запуск игры:

 60°C @ 69 PWM, changing to  90.
 59°C @ 89 PWM, changing to  70.
 60°C @ 69 PWM, changing to  90.
 57°C @ 89 PWM, changing to  70.
 54°C @ 69 PWM.
 59°C @ 69 PWM.
 62°C @ 69 PWM, changing to  90.
 77°C @ 89 PWM.

Активная фаза игры:

 82°C @ 89 PWM, changing to 140.
 62°C @138 PWM, changing to  90.
 59°C @ 89 PWM, changing to  70.
 62°C @ 69 PWM, changing to  90.
 60°C @ 89 PWM.
...
 61°C @ 89 PWM.
 62°C @ 89 PWM.
 58°C @ 89 PWM, changing to  70.
 60°C @ 69 PWM, changing to  90.
 75°C @ 89 PWM.

Игра завершена, плавное падение температуры:

 53°C @ 89 PWM, changing to  70.
 52°C @ 69 PWM.
 40°C @ 69 PWM.
 39°C @ 69 PWM, changing to   0.
 40°C @  0 PWM, changing to  70.
 39°C @ 69 PWM, changing to   0.
 39°C @  0 PWM.

Ночь — колебания 35-38°C с отключёнными вентиляторами видюхи.

Утро — вход в систему, веб-сёрфинг, редактирование и пр.:

 40°C @  0 PWM, changing to  70.
 41°C @ 69 PWM.

Далее — колебания 42-55°C при ШИМ 69.

На данный момент за компом никого, но на улице уже под тридцатник:

мая 25 14:37:14 comp.ill amdgpufan[2340226]:  40°C @  0 PWM.
мая 25 14:37:19 comp.ill amdgpufan[2340226]:  41°C @  0 PWM, changing to  70.
мая 25 14:37:24 comp.ill amdgpufan[2340226]:  40°C @ 69 PWM, changing to   0.
мая 25 14:37:29 comp.ill amdgpufan[2340226]:  40°C @  0 PWM.
мая 25 14:37:34 comp.ill amdgpufan[2340226]:  40°C @  0 PWM.
мая 25 14:37:39 comp.ill amdgpufan[2340226]:  40°C @  0 PWM.
мая 25 14:37:44 comp.ill amdgpufan[2340226]:  40°C @  0 PWM.
мая 25 14:37:49 comp.ill amdgpufan[2340226]:  41°C @  0 PWM, changing to  70.
мая 25 14:37:54 comp.ill amdgpufan[2340226]:  40°C @ 69 PWM, changing to   0.
мая 25 14:37:59 comp.ill amdgpufan[2340226]:  40°C @  0 PWM.

Перезапуск скрипта в жару (после автонастройки ШИМ на нуле при 48°C):

мая 25 17:37:16 comp.ill amdgpufan[2541583]:  49°C @ 69 PWM.
мая 25 17:37:20 comp.ill systemd[1]: Stopping AMD GPU fan control...
мая 25 17:37:20 comp.ill amdgpufan[2541583]: Завершено
мая 25 17:37:20 comp.ill amdgpufan[2541583]: Exiting and setting fan mode to 'auto'.
мая 25 17:37:20 comp.ill systemd[1]: amdgpufan.service: Deactivated successfully.
мая 25 17:37:20 comp.ill systemd[1]: Stopped AMD GPU fan control.
мая 25 17:37:20 comp.ill systemd[1]: Started AMD GPU fan control.
мая 25 17:37:20 comp.ill amdgpufan[2543433]: Wrong fan mode, setting to 'manual'.
мая 25 17:37:20 comp.ill amdgpufan[2543433]:  48°C @  0 PWM, changing to  90.
мая 25 17:37:25 comp.ill amdgpufan[2543433]:  48°C @ 89 PWM.

Выводы

На данный момент вечерами, по прохладе, большой внешний вентилятор уже точно не нужен: игрушки на ультрах в высоком разрешении прогревают самый горячий компонент видюхи не выше 90 градусов, тогда как прежде и с вентилятором за сотку вылезало. Как оно в дневную жару, опробовать пока не довелось, но по результатам отчитаюсь.

Когда не ломанная / не чиненная железяка работает не так, как ожидается, порой на помощь спешат чип и... программные средства. Пусть без рюшечек и фантиков, зато задача решена на системном уровне. Ну, и есть надежда, что дружелюбного софта тоже не придётся долго ждать.

Послесловие

А ведь есть ещё варианты разгона с понижением напруги типа такого. С учётом побеждённого перегрева, отчего б и его не задействовать... :)