Skip to content

Instantly share code, notes, and snippets.

@Jipok
Last active February 3, 2024 06:57
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Jipok/855fddcb0055f531d9260b715648e966 to your computer and use it in GitHub Desktop.
Save Jipok/855fddcb0055f531d9260b715648e966 to your computer and use it in GitHub Desktop.
TUI with chart for radeon power cap control, temp monitoring
#!/usr/bin/env python3
import plotext as plt
from subprocess import check_output
import psutil
import time
CMD = "sensors amdgpu-pci-0500 | grep PPT | grep -oP '(?<=cap =) *(.?\d+)'"
TARGET_TEMP = 83
CRITICAL_TEMP = 92
CAP_MIN = 2
CAP_MAX = 180
CHART_HISTORY_COUNT = 55
plt.theme("pro")
# Prefill arrays for good chart after start
a_temp = [43]
a_powercap = [180]
temp = psutil.sensors_temperatures()["amdgpu"][0].current
powercap = int(check_output(CMD, shell = True).decode('utf-8'))
for i in range(1, CHART_HISTORY_COUNT):
a_temp.append(temp)
a_powercap.append(powercap)
while True:
# Trim chart
if len(a_temp) > CHART_HISTORY_COUNT:
a_temp = a_temp[1:]
a_powercap = a_powercap[1:]
# Get data
temp = psutil.sensors_temperatures()["amdgpu"][0].current
a_temp.append(temp)
powercap = int(check_output(CMD, shell = True).decode('utf-8'))
a_powercap.append(powercap)
# Plot temp
plt.clear_terminal()
plt.clear_data()
label = "Temp %s°C" % temp
plt.plot(a_temp, label = label, color = "red")
plt.ylabel(label)
plt.ylim(20, 100)
plt.hline(TARGET_TEMP, "green")
# Plot power cap
label = "Powercap %sW" % powercap
plt.plot(a_powercap, label = label, yside = "right", color = "blue")
plt.ylabel(label, yside = "right")
plt.ylim(CAP_MIN - 10, CAP_MAX + 10, yside = "right")
plt.show()
# Hard save
if temp >= CRITICAL_TEMP:
# Kill all non-root(avoid suicide) python processes
check_output('ps -ef | grep "[p]ython" | awk \'$1!="root" {print $2}\' | xargs -r kill -9', shell = True)
# Limit power
newcap = powercap
if temp < TARGET_TEMP:
cap_step = TARGET_TEMP - temp
newcap = int(min(powercap + cap_step, CAP_MAX))
if temp > TARGET_TEMP:
cap_step = pow(temp - TARGET_TEMP, 2)
newcap = int(max(powercap - cap_step, CAP_MIN))
if newcap != powercap:
check_output("/opt/rocm/bin/rocm-smi --setpoweroverdrive " + str(newcap), shell = True)
time.sleep(1)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment