Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save Jiab77/1b9c32d550ebb93c471a8fa5b92cf2bf to your computer and use it in GitHub Desktop.
Save Jiab77/1b9c32d550ebb93c471a8fa5b92cf2bf to your computer and use it in GitHub Desktop.
How to control BOINC workload based on the host temperature

How to control BOINC workload based on the host temperature

I will explain here how to start and stop boinc depending on the host temperature.

Context

I'm actually using a NUC to run BOINC and the Rosetta@Home project but this host is getting hot very quick and sometimes it will shutdown because of overheating.

To avoid this, I've requested the help of @AenBleidd, one of the BOINC developers. He gave me idea to use lm-sensors and CRON to run a script that will start / stop BOINC.

Based on his idea, I've made the job 😉

Install dependencies

To read the host temperature I'll use lm-sensors as adviced by @AenBleidd.

# Install lm-sensors
sudo apt install lm-sensors

# Detect active sensors
sudo sensors-detect

# Run a small test
sensors

# It should return something like that:
coretemp-isa-0000
Adapter: ISA adapter
Package id 0:  +42.0°C  (high = +100.0°C, crit = +100.0°C)
Core 0:        +42.0°C  (high = +100.0°C, crit = +100.0°C)
Core 1:        +39.0°C  (high = +100.0°C, crit = +100.0°C)

Unfortunately lm-sensors is not working on Raspberry Pi devices so I moved back on the ACPI thermal zone information.

Test on Raspberry Pi's:

# Get raw temperature
cat /sys/class/thermal/thermal_zone*/temp

# Get raw rounded temperature value
cat /sys/class/thermal/thermal_zone*/temp | sed 's/\(.\)..$//'

# Get formatted temperature
cat /sys/class/thermal/thermal_zone*/temp | sed 's/\(.\)..$/.\1°C/'

The command above are based on this post: https://askubuntu.com/questions/15832/how-do-i-get-the-cpu-temperature/854029#854029

Create control script

Create a script named boinctempctl and the following content:

#!/bin/bash

# Default config
CONFIG_FILE=/etc/boinctempctl.conf
LOG_FILE=/tmp/boinctempctl.log
LOG_DATE=$(date +"%c")

# Detect Raspberry Pi's
IS_RPI=$(cat /proc/cpuinfo | grep -i bcm2835 > /dev/null ; echo $?)

# Set current temperature based on the device type
if [[ $IS_RPI -eq 0 ]]; then
	# Value in celsius degrees
	CUR_TEMP=$(cat /sys/class/thermal/thermal_zone*/temp | sed 's/\(.\)..$//')
else
	# Value in celsius degrees
	CUR_TEMP=$(sensors -u | grep -i temp1_input | cut -d' ' -f4)
fi

# Default limits in celsius degrees
MAX_TEMP=80
MIN_TEMP=40

# Reading config file
[[ -f $CONFIG_FILE ]] && source $CONFIG_FILE

# Check environment
if [ ! -t 1 ]; then
    FROM_CRON=true
else
    FROM_CRON=false
fi

# Show current temperature
[[ $FROM_CRON == false ]] && echo -e "\nCurrent temperature: ${CUR_TEMP/.000/}°c"
echo -e "\n$LOG_DATE Current temperature: ${CUR_TEMP/.000/}°c" >> $LOG_FILE

# Stop computing if the temp is going too high
if [[ ${CUR_TEMP/.000/} -ge $MAX_TEMP ]]; then
    [[ $FROM_CRON == false ]] && echo -e "\nHost is overheating, computing will be stopped.\n"
    echo "$LOG_DATE Host is overheating, computing will be stopped." >> $LOG_FILE
    if [[ $(systemctl status boinc-client.service | grep -i "active: active" | wc -l) -gt 0 ]]; then
        systemctl stop boinc-client.service
        #boinccmd --quit
    fi
else
    if [[ $(systemctl status boinc-client.service | grep -i "active: active" | wc -l) -gt 0 ]]; then
        [[ $FROM_CRON == false ]] && echo -e "\nHost temperature is correct, keep computing...\n"
        echo "$LOG_DATE Host temperature is correct, keep computing..." >> $LOG_FILE
    else
        [[ $FROM_CRON == false ]] && echo -e "\nHost is cooling down before restart computing...\n"
        echo "$LOG_DATE Host is cooling down before restart computing..." >> $LOG_FILE
    fi
fi

# Start computing when the temp is low enough
if [[ ${CUR_TEMP/.000/} -le $MIN_TEMP && ${CUR_TEMP/.000/} -lt $MAX_TEMP ]]; then
    [[ $FROM_CRON == false ]] && echo -e "\nHost is fresh enough, start computing.\n"
    echo "$LOG_DATE Host is fresh enough, start computing." >> $LOG_FILE
    if [[ $(systemctl status boinc-client.service | grep -i "active: active" | wc -l) -eq 0 ]]; then
        systemctl start boinc-client.service
    fi
fi

Then make it executable: chmod -v +x boinctempctl.

Create config file

The updated script now support configuration file. Change the CONFIG_FILE variable to change the path.

sudo nano /etc/boinctempctl.conf

Add the following content:

# boinctempctl config file
# Value in celsius degrees
MAX_TEMP=85
MIN_TEMP=45

# log file
LOG=/tmp/boinctempctl.log

You can change the default values to anything you want.

Installation

You can run the script locally but it will require sudo privilege to start / stop the service.

Per user

cp -v boinctempctl /home/[user]/

System wide

sudo cp -v boinctempctl /usr/bin/

Create CRON task

Now create a CRON task with sudo crontab -e and add the following content:

*/1 * * * * /home/[USER]/boinctempctl

Replace [USER] by your user.

If you have decided to install the script system wide, then change the path to: /usr/bin/boinctempctl.

And that's all! 🎉

The script will automatically create a log file that you can read with tail -f /tmp/boinctempctl.log.

tail -f /tmp/boinctempctl.log

Wed 22 Apr 2020 01:18:01 AM CEST Host is cooling down before restart computing...

Wed 22 Apr 2020 01:19:01 AM CEST Current temperature: 52°c
Wed 22 Apr 2020 01:19:01 AM CEST Host is cooling down before restart computing...

Wed 22 Apr 2020 01:20:01 AM CEST Current temperature: 48°c
Wed 22 Apr 2020 01:20:01 AM CEST Host is cooling down before restart computing...

Wed 22 Apr 2020 01:21:01 AM CEST Current temperature: 48°c
Wed 22 Apr 2020 01:21:01 AM CEST Host is cooling down before restart computing...

Usage

You can also simply run the script without CRON. Here are some examples:

# Run the script manually
sudo ./boinctempctl

Wed 22 Apr 2020 01:21:01 AM CEST Current temperature: 48°c
Wed 22 Apr 2020 01:21:01 AM CEST Host is cooling down before restart computing...

# Or like CRON but with watch and below than a minute
watch -n 10 'sudo ./boinctempctl ; tail /tmp/boinctempctl.log'

# Hit [Ctrl + C] to exit

If you have decided to install the script system wide, then change the path to: /usr/bin/boinctempctl.

Thanks

Thanks again to @AenBleidd who helped me with his brilliant idea to use lm-sensors and CRON.

References

Contribute

Feel free to create a comment to contribute on this gist.

Contact

You can reach me on Twitter by using @Jiab77.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment