<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://wiki.domoticz.com/index.php?action=history&amp;feed=atom&amp;title=Raspberry_pi_fan_control_and_monitoring_with_bash</id>
	<title>Raspberry pi fan control and monitoring with bash - Revision history</title>
	<link rel="self" type="application/atom+xml" href="https://wiki.domoticz.com/index.php?action=history&amp;feed=atom&amp;title=Raspberry_pi_fan_control_and_monitoring_with_bash"/>
	<link rel="alternate" type="text/html" href="https://wiki.domoticz.com/index.php?title=Raspberry_pi_fan_control_and_monitoring_with_bash&amp;action=history"/>
	<updated>2026-09-18T20:44:09Z</updated>
	<subtitle>Revision history for this page on the wiki</subtitle>
	<generator>MediaWiki 1.46.0</generator>
	<entry>
		<id>https://wiki.domoticz.com/index.php?title=Raspberry_pi_fan_control_and_monitoring_with_bash&amp;diff=7890&amp;oldid=prev</id>
		<title>Lomax: /* Hardware */</title>
		<link rel="alternate" type="text/html" href="https://wiki.domoticz.com/index.php?title=Raspberry_pi_fan_control_and_monitoring_with_bash&amp;diff=7890&amp;oldid=prev"/>
		<updated>2017-02-05T18:52:16Z</updated>

		<summary type="html">&lt;p&gt;&lt;span class=&quot;autocomment&quot;&gt;Hardware&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;b&gt;New page&lt;/b&gt;&lt;/p&gt;&lt;div&gt;&lt;br /&gt;
== Purpose ==&lt;br /&gt;
&lt;br /&gt;
If you&amp;#039;re not using the on-board audio, you can take advantage of the hardware [https://en.wikipedia.org/wiki/Pulse_width_modulation Pulse Width Modulation] capabilities of the Raspberry Pi to control the speed of a small PC fan, based on the system temperature. The fan&amp;#039;s status is monitored and logged in Domoticz (and in the syslog). Note that this script is not dependent on Domoticz in any way other than for monitoring. It is launched and runs independently, so that if Domoticz should stop running, for whatever reason, the script will continue to quietly do its thing, keeping your system cool.&lt;br /&gt;
&lt;br /&gt;
== Dependencies ==&lt;br /&gt;
&lt;br /&gt;
First you&amp;#039;ll need to get the PWM activated, which unfortunately isn&amp;#039;t as straightforward as one might think; the hardware PWM clock is not initialised at boot, and by default only starts up when the on-board soundcard is in use. There is however an alternative Device Tree Overlay, which activates the hardware PWM clock for general use, see the following guide for how to install it: [http://www.jumpnowtek.com/rpi/Using-the-Raspberry-Pi-Hardware-PWM-timers.html Using the Raspberry Pi hardware PWM timers]. You could of course use a &amp;quot;soft&amp;quot; PWM instead, but these eat up precious CPU cycles, which seems unnecessary when you just want to change the speed of a fan - so this guide assumes the hardware PWM route. &lt;br /&gt;
&lt;br /&gt;
Once you have installed and activated the pwm-with-clk.dtbo overlay linked to above, you should be able to test the PWM by doing (in a root shell):&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
# cd to the device location&lt;br /&gt;
cd /sys/class/pwm/pwmchip0&lt;br /&gt;
&lt;br /&gt;
# Export PWM channel 0&lt;br /&gt;
echo 0 &amp;gt; export&lt;br /&gt;
&lt;br /&gt;
# Set the period in nanoseconds&lt;br /&gt;
echo 1000000 &amp;gt; pwm0/period&lt;br /&gt;
&lt;br /&gt;
# Set the duty cycle &amp;lt;= period&lt;br /&gt;
echo 200000 &amp;gt; pwm0/duty_cycle&lt;br /&gt;
&lt;br /&gt;
# Enable the PWM&lt;br /&gt;
echo 1 &amp;gt; pwm0/enable&lt;br /&gt;
&lt;br /&gt;
# Duty cycle can be changed while running&lt;br /&gt;
echo 999999 &amp;gt; pwm0/duty_cycle&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
=== Domoticz configuration ===&lt;br /&gt;
&lt;br /&gt;
To be able to monitor the fan status in Domoticz, you need to create a &amp;quot;virtual sensor&amp;quot; of the type &amp;quot;Alert&amp;quot;. Call it &amp;quot;Fan Status&amp;quot; for example, and make note of its index number (shown on the &amp;quot;Devices&amp;quot; page in Domoticz). &lt;br /&gt;
&lt;br /&gt;
== Hardware ==&lt;br /&gt;
&lt;br /&gt;
If you have access to an oscilloscope, correct functioning of the hardware PWM can be verified by hooking it up to the pin you chose when enabling the overlay (pwm0 defaults to GPIO_18). Otherwise, you can hook up an LED with a small series resistor (270 Ω) between the PWM pin and a GND pin; by modifying the &amp;quot;duty_cycle&amp;quot; value above you should see the light intensity change. But an output pin on a Raspberry Pi is not powerful enough to directly drive a fan, nor is the voltage sufficient for most PC type fans, which tend to run on 12 V DC (though 5 V varieties also exist). So we will need some external cicuitry to give it a bit more brawn: &lt;br /&gt;
&lt;br /&gt;
[[File:pwm_driver_circuit.png||A simple MOSFET PWM fan driver circuit]]&lt;br /&gt;
&lt;br /&gt;
Suggested components:&lt;br /&gt;
* Q1: any small N-channel MOSFET (e.g. 2N7000/BS170)&lt;br /&gt;
* R1: 10 kΩ resistor&lt;br /&gt;
* C1: 0.1 uF electrolytic capacitor&lt;br /&gt;
* D1: Any small rectifier diode&lt;br /&gt;
&lt;br /&gt;
Nothing too complicated going on there; Q1 will be switched on/off by the PWM signal from the Pi, C1 &amp;amp; D1 smooth out transients, while R1 keeps the MOSFET gate from floating. You can build this on an 8x4 piece of stripboard: &lt;br /&gt;
&lt;br /&gt;
[[File:pwm_driver_stripboard.png||Stripboard layout]]&lt;br /&gt;
&lt;br /&gt;
The &amp;quot;RPM&amp;quot; line is just a straight through connection, in case you want to use a [http://pcbheaven.com/wikipages/How_PC_Fans_Work/ 3-pin fan] with tachometer output. You can connect this to an input pin on the RasPi if you want to read it, but you&amp;#039;ll need to enable the internal pull-up resistor for it to work (the tachometer output on PC fans is an [https://en.wikipedia.org/wiki/Open_collector open collector]). &lt;br /&gt;
&lt;br /&gt;
To connect it up, run a wire from the PWM output pin on the Pi (the default is GPIO_18 for pwm0, though you can change this in /boot/config.txt) to the PWM input connector on the stripboard. If your fan is a 12 V model you&amp;#039;ll need a separate 12 V power supply, which you connect to the GND and VDC inputs. If it&amp;#039;s a 5 V model, you can probably get away with powering it from the 5 V pin on the Pi, provided it has a sufficiently powerful PSU - in this case connect the GND input to one of the ground pins on the Pi, and VDC to the Pi&amp;#039;s 5 V pin.&lt;br /&gt;
&lt;br /&gt;
Optionally, if you want to monitor the fan&amp;#039;s rotational speed, connect a wire from an input pin on the Pi to the RPM pin on the stripboard, and activate its internal pull-up resistor. &amp;#039;&amp;#039;Since it&amp;#039;s not possible to do this from a Bash script, this functionality is not currently supported by the script featured here.&amp;#039;&amp;#039; If you want to include RPM monitoring you&amp;#039;ll need to install a GPIO library, such as [http://wiringpi.com WiringPi], and modify the script to count RPM pulses, and report these to Domoticz in a separate virtual sensor.&lt;br /&gt;
&lt;br /&gt;
== Installation instructions ==&lt;br /&gt;
&lt;br /&gt;
Assuming you have followed the instructions for [http://www.jumpnowtek.com/rpi/Using-the-Raspberry-Pi-Hardware-PWM-timers.html activating the PWM hardware clock at boot], all you need to do is copy the script below into a new file on your Pi, change the &amp;quot;fan_idx&amp;quot; to the index of the Domoticz alert sensor you want to use for monitoring, and make it executable:&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
sudo nano /usr/local/bin/fancontrol.sh&lt;br /&gt;
# Paste the script into this file and save it&lt;br /&gt;
# Make it executable with&lt;br /&gt;
sudo chmod u+x /usr/local/bin/fancontrol.sh&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You can now test the script by running:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
sudo /usr/local/bin/fancontrol.sh&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Leave the script running, and in another terminal run (for example) &amp;quot;stress&amp;quot; to load the CPU, causing it to heat up:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
stress --cpu 4&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
You should see the fan start spinning, and after stopping &amp;quot;stress&amp;quot;, eventually stop. You should also see the status of the &amp;quot;alert&amp;quot; sensor you set up in Domoticz change when the fan status changes. Open the script and edit the temperature breakpoints, and low/high fan-speeds to suit. Note that the fan-speed should never exceed the &amp;quot;period&amp;quot; value (&amp;quot;period&amp;quot; is the PWM frequency in nanoseconds, so 100000 is 1 kHz), and if you set it too low it may not provide enough energy for the fan to start. &lt;br /&gt;
&lt;br /&gt;
Finally, you probably want to launch this script at boot, and leave it running in the background. On a Systemd Linux distribution (like Raspbian), this is very simple; create a new file in /etc/systemd/system/ called fancontrol.service:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
sudo nano /etc/systemd/system/fancontrol.service&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
And paste the following into it: &lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
[Unit]&lt;br /&gt;
After=multi-user.target&lt;br /&gt;
&lt;br /&gt;
[Service]&lt;br /&gt;
ExecStart=/usr/local/bin/fancontrol.sh&lt;br /&gt;
&lt;br /&gt;
[Install]&lt;br /&gt;
WantedBy=default.target&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
Again, make this executable with: &lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
sudo chmod u+x /etc/systemd/system/fancontrol.service&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
You then need to tell Systemd about the new service, and enable it to run at boot:&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
sudo systemctl daemon-reload&lt;br /&gt;
sudo systemctl enable fancontrol&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
That&amp;#039;s all there is to it - you can now try rebooting your system and checking if the fancontrol service is running with: &lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
sudo systemctl status fancontrol&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Script with comments ==&lt;br /&gt;
&lt;br /&gt;
&amp;lt;syntaxhighlight lang=&amp;quot;bash&amp;quot;&amp;gt;&lt;br /&gt;
#!/bin/bash&lt;br /&gt;
&lt;br /&gt;
# Device references&lt;br /&gt;
dev_temp=/sys/class/thermal/thermal_zone0/temp&lt;br /&gt;
dev_pwm=/sys/class/pwm/pwmchip0/pwm0&lt;br /&gt;
dev_enable=$dev_pwm/enable&lt;br /&gt;
dev_duty=$dev_pwm/duty_cycle&lt;br /&gt;
dev_period=$dev_pwm/period&lt;br /&gt;
&lt;br /&gt;
# Export pwm0 if it&amp;#039;s not available&lt;br /&gt;
if [ ! -e $dev_pwm ]; then&lt;br /&gt;
    echo 0 &amp;gt; /sys/class/pwm/pwmchip0/export&lt;br /&gt;
    sleep 2&lt;br /&gt;
fi&lt;br /&gt;
&lt;br /&gt;
# PWM frequency (nanoseconds)&lt;br /&gt;
period=1000000&lt;br /&gt;
&lt;br /&gt;
# temperature breakpoints (millidegrees)&lt;br /&gt;
off_low=34000&lt;br /&gt;
low_off=30000&lt;br /&gt;
low_high=40000&lt;br /&gt;
high_low=36000&lt;br /&gt;
&lt;br /&gt;
# fan-speed (nanoseconds)&lt;br /&gt;
low=300000&lt;br /&gt;
high=999999&lt;br /&gt;
&lt;br /&gt;
# on/off values&lt;br /&gt;
off=0&lt;br /&gt;
on=1&lt;br /&gt;
&lt;br /&gt;
# domoticz configuration&lt;br /&gt;
domoticz=&amp;quot;https://127.0.0.1&amp;quot;&lt;br /&gt;
fan_idx=31&lt;br /&gt;
&lt;br /&gt;
# update interval (seconds)&lt;br /&gt;
interval = 10&lt;br /&gt;
&lt;br /&gt;
# initialise the fan&lt;br /&gt;
next=($off $low)&lt;br /&gt;
echo $period &amp;gt; $dev_period&lt;br /&gt;
echo ${next[0]} &amp;gt; $dev_enable&lt;br /&gt;
echo ${next[1]} &amp;gt; $dev_duty&lt;br /&gt;
&lt;br /&gt;
update_status() {&lt;br /&gt;
    if [[ $(cat $dev_enable) == 1 ]]; then&lt;br /&gt;
        if [[ $(cat $dev_duty) == $high ]]; then&lt;br /&gt;
            nvalue=3&lt;br /&gt;
            svalue=&amp;quot;High&amp;quot;&lt;br /&gt;
        else&lt;br /&gt;
            nvalue=2&lt;br /&gt;
            svalue=&amp;quot;Low&amp;quot;&lt;br /&gt;
        fi&lt;br /&gt;
    else&lt;br /&gt;
        nvalue=1&lt;br /&gt;
        svalue=&amp;quot;Off&amp;quot;&lt;br /&gt;
    fi&lt;br /&gt;
    logger &amp;quot;Fan $svalue&amp;quot;&lt;br /&gt;
    curl -s -k &amp;quot;&amp;quot;$domoticz&amp;quot;/json.htm?type=command&amp;amp;param=udevice&amp;amp;idx=&amp;quot;$fan_idx&amp;quot;&amp;amp;nvalue=&amp;quot;$nvalue&amp;quot;&amp;amp;svalue=&amp;quot;$svalue&amp;quot;&amp;quot; &amp;gt; /dev/null&lt;br /&gt;
}&lt;br /&gt;
&lt;br /&gt;
while [ : ]&lt;br /&gt;
do&lt;br /&gt;
    temp=$(cat $dev_temp)&lt;br /&gt;
    current=($(cat $dev_enable) $(cat $dev_duty))&lt;br /&gt;
    if [ $temp -gt $off_low ]; then&lt;br /&gt;
        next[0]=$on&lt;br /&gt;
        if [ $temp -gt $low_high ]; then&lt;br /&gt;
            next[1]=$high&lt;br /&gt;
        elif [ $temp -lt $high_low ]; then&lt;br /&gt;
            next[1]=$low&lt;br /&gt;
        fi&lt;br /&gt;
    elif [ $temp -lt $low_off ]; then&lt;br /&gt;
        next[0]=$off&lt;br /&gt;
    fi&lt;br /&gt;
    &lt;br /&gt;
    if [ &amp;quot;${next[*]}&amp;quot; != &amp;quot;${current[*]}&amp;quot; ]; then&lt;br /&gt;
        echo ${next[1]} &amp;gt; $dev_duty&lt;br /&gt;
        echo ${next[0]} &amp;gt; $dev_enable&lt;br /&gt;
        update_status&lt;br /&gt;
    fi&lt;br /&gt;
    sleep $interval&lt;br /&gt;
done&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== Link to forum post ==&lt;br /&gt;
&lt;br /&gt;
There is a topic in the forum if you wish to discuss this script, or if you need help getting it to work: [http://www.domoticz.com/forum/viewtopic.php?f=63&amp;amp;t=15929 Raspberry Pi hardware PWM fan control and monitoring].&lt;br /&gt;
&lt;br /&gt;
--[[User:Lomax|Lomax]] ([[User talk:Lomax|talk]]) 18:38, 5 February 2017 (CET)&lt;br /&gt;
&lt;br /&gt;
[[Category:Scripting‏‎]]&lt;br /&gt;
[[Category:Bash‏‎]]&lt;br /&gt;
&lt;br /&gt;
[[Category:Linux]]&lt;br /&gt;
[[Category:Raspberry Pi]]&lt;br /&gt;
&lt;br /&gt;
[[Category:Hardware]]&lt;/div&gt;</summary>
		<author><name>Lomax</name></author>
	</entry>
</feed>