forked from Sepero/temp-throttle
-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathtemp_throttle.sh
executable file
·207 lines (168 loc) · 6.29 KB
/
temp_throttle.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
#!/bin/bash
# Usage: temp_throttle.sh max_temp
# USE CELSIUS TEMPERATURES.
# version 2.21
cat << EOF
Author: Sepero 2016 (sepero 111 @ gmx . com)
URL: http://github.com/Sepero/temp-throttle/
EOF
# Additional Links
# http://seperohacker.blogspot.com/2012/10/linux-keep-your-cpu-cool-with-frequency.html
# Additional Credits
# Wolfgang Ocker <weo AT weo1 DOT de> - Patch for unspecified cpu frequencies.
# Additional Credits
# ps1code <[email protected]> - Patch for checking all cores for max
# temperature instead of the first three.
# ps1code <[email protected]> - New feature, can now use lm-sensors (tested on v3.06)
# to get cpu temperature
# License: GNU GPL 2.0
# Generic function for printing an error and exiting.
err_exit () {
echo ""
echo "Error: $@" 1>&2
exit 128
}
if [ $# -lt 1 ]; then
# If temperature wasn't given, then print a message and exit.
echo "Please supply a maximum desired temperature in Celsius." 1>&2
echo "For example: ${0} 60" 1>&2
echo "You can add second argument to grab cpu temperature from lm-sensors instead." 1>&2
echo "For example: ${0} 60 lm-sensors" 1>&2
exit 2
else
#Set the first argument as the maximum desired temperature.
MAX_TEMP=$1
LM_SENSORS=$2
echo "Using Parameters: $MAX_TEMP $LM_SENSORS" 1>&2
fi
### START Initialize Global variables.
# The frequency will increase when low temperature is reached.
LOW_TEMP=$((MAX_TEMP - 5))
CORES=$(nproc) # Get number of CPU cores.
echo -e "Number of CPU cores detected: $CORES\n"
CORES=$((CORES - 1)) # Subtract 1 from $CORES for easier counting later.
# Temperatures internally are calculated to the thousandth.
MAX_TEMP=${MAX_TEMP}000
LOW_TEMP=${LOW_TEMP}000
# Lets write it out to be changed dynamically
MAX_TEMP_FILE_LOC="/tmp/temp_throttle/max_temp"
LOW_TEMP_FILE_LOC="/tmp/temp_throttle/low_temp"
mkdir -p /tmp/temp_throttle
echo $MAX_TEMP 2> /dev/null > $MAX_TEMP_FILE_LOC
echo $LOW_TEMP 2> /dev/null > $LOW_TEMP_FILE_LOC
if [ "$LM_SENSORS" == "lm-sensors" ]; then
LM_SENSORS=true
if ! sensors > /dev/null; then
err_exit "lm-sensors not installed or sensors not in PATH."
fi
echo "Using lm-sensors" 1>&2
else
LM_SENSORS=false
fi
FREQ_FILE="/sys/devices/system/cpu/cpu0/cpufreq/scaling_available_frequencies"
FREQ_MIN="/sys/devices/system/cpu/cpu0/cpufreq/cpuinfo_min_freq"
FREQ_MAX="/sys/devices/system/cpu/cpu0/cpufreq/cpuinfo_max_freq"
# Store available cpu frequencies in a space separated string FREQ_LIST.
if [ -f $FREQ_FILE ]; then
# If $FREQ_FILE exists, get frequencies from it.
FREQ_LIST=$(cat $FREQ_FILE | xargs -n1 | sort -g -r | xargs) || err_exit "Could not read available cpu frequencies from file $FREQ_FILE"
elif [ -f $FREQ_MIN -a -f $FREQ_MAX ]; then
# Else if $FREQ_MIN and $FREQ_MAX exist, generate a list of frequencies between them.
FREQ_LIST=$(seq $(cat $FREQ_MAX) -100000 $(cat $FREQ_MIN)) || err_exit "Could not compute available cpu frequencies"
else
err_exit "Could not determine available cpu frequencies"
fi
FREQ_LIST_LEN=$(echo $FREQ_LIST | wc -w)
# CURRENT_FREQ will save the index of the currently used frequency in FREQ_LIST.
CURRENT_FREQ=2
# Get all files that stores temperature information for all cores.
START=0
for (( c=$START; c<$CORES; c++ ))
do
# Possible locations to read the current system temperature.
TF=${TF}"/sys/class/thermal/thermal_zone${c}/temp "
TF=${TF}"/sys/class/hwmon/hwmon${c}/temp1_input "
TF=${TF}"/sys/class/hwmon/hwmon${c}/device/temp1_input "
done
TEMPERATURE_FILES=${TF}
# Store the first temperature location that exists in the variable TEMP_FILE.
# The location stored in $TEMP_FILE will be used for temperature readings.
for file in $TEMPERATURE_FILES; do
TEMP_FILE=$file
[ -f $TEMP_FILE ] && break
done
[ $TEMP_FILE == "null" ] && err_exit "The location for temperature reading was not found."
### END Initialize Global variables.
### START define script functions.
# Set the maximum frequency for all cpu cores.
set_freq () {
# From the string FREQ_LIST, we choose the item at index CURRENT_FREQ.
FREQ_TO_SET=$(echo $FREQ_LIST | cut -d " " -f $CURRENT_FREQ)
echo $FREQ_TO_SET
for i in $(seq 0 $CORES); do
# Try to set core frequency by writing to /sys/devices.
{ echo $FREQ_TO_SET 2> /dev/null > /sys/devices/system/cpu/cpu$i/cpufreq/scaling_max_freq; } ||
# Else, try to set core frequency using command cpufreq-set.
{ cpufreq-set -c $i --max $FREQ_TO_SET > /dev/null; } ||
# Else, return error message.
{ err_exit "Failed to set frequency CPU core$i. Run script as Root user. Some systems may require to install the package cpufrequtils."; }
done
}
# Will reduce the frequency of cpus if possible.
throttle () {
if [ $CURRENT_FREQ -lt $FREQ_LIST_LEN ]; then
CURRENT_FREQ=$((CURRENT_FREQ + 1))
echo -n "throttle "
set_freq $CURRENT_FREQ
fi
}
# Will increase the frequency of cpus if possible.
unthrottle () {
if [ $CURRENT_FREQ -ne 1 ]; then
CURRENT_FREQ=$((CURRENT_FREQ - 1))
echo -n "unthrottle "
set_freq $CURRENT_FREQ
fi
}
get_temp () {
# Get the system temperature. Take the max of all counters
if [ "$LM_SENSORS" == "true" ]; then
TEMP=$(sensors | grep -A 0 'CPU T' | cut -d' ' -f 6 | sed 's/+//' | sed 's/°C//')
TEMP=$(echo "$TEMP/1" | bc)000
else
TEMP=$(cat $TEMPERATURE_FILES 2>/dev/null | xargs -n1 | sort -g -r | head -1)
fi
echo "Current Temp: $TEMP"
}
### END define script functions.
echo "Initialize to max CPU frequency"
unthrottle
# Main loop
while true; do
get_temp # Gets the current temperature and set it to the variable TEMP.
if [ $TEMP -gt $MAX_TEMP ]; then # Throttle if too hot.
throttle
elif [ $TEMP -le $LOW_TEMP ]; then # Unthrottle if cool.
unthrottle
fi
sleep 5 # The amount of time between checking temperatures.
# Allow for dynamic max temperature.
if [[ -f "$MAX_TEMP_FILE_LOC" ]]; then
MAX_TEMP=$(cat $MAX_TEMP_FILE_LOC 2> /dev/null)
if [[ $LOW_TEMP -gt $MAX_TEMP || $LOW_TEMP -eq $MAX_TEMP ]]; then
LOW_TEMP="$((MAX_TEMP-5000))"
echo $LOW_TEMP > $LOW_TEMP_FILE_LOC
echo "LOW TEMP ADUSTED TO: $LOW_TEMP"
fi
echo "MAX TEMP: $MAX_TEMP"
fi
if [[ -f "$LOW_TEMP_FILE_LOC" ]]; then
LOW_TEMP=$(cat $LOW_TEMP_FILE_LOC 2> /dev/null)
if [[ $LOW_TEMP -gt $MAX_TEMP || $LOW_TEMP -eq $MAX_TEMP ]]; then
LOW_TEMP="$((MAX_TEMP-5000))"
echo $LOW_TEMP > $LOW_TEMP_FILE_LOC
echo "LOW TEMP ADUSTED TO: $LOW_TEMP"
fi
echo "LOW_TEMP: $LOW_TEMP"
fi
done