R Pi 4 Temperature and Load Log

For info email

Ref: Support PWM to control speed? #22 on Pimorini Fan Shim Support

I have been experimenting with PWM and the Pimorini Fan Shim.  I will make a Zip of the Python once I and fully debugged it and put here. However there is enough info on this page to have a go.   The result is shown in the window below and in this csv file

I tested with finding the maximum frequency for each range of pwm speeds that always gets the fan going continuously (see below). For lower pwm % you need a lower frequency for the fan to spin at all but not too low so that its running intermittently. Very low speed values are not really worth bothering with (little cooling effect) so I start at 20%.

Its a rather nice result with the Fan spinning nice and calmly most of the time and never intermittently.
The speed is updated at a very slow rate (about every minute and a half) normally but a check is made every 5 sec in case temperature is above a threshold and then for as long as temp is high speed is updated every 5 seconds.

On a full load CPU test it settles at around 60% speed and about 65C.
For long periods the fan does not run at all.

speed calc is speed = 20 + 80 * (cpu.temp - min_temp)/(max_temp - min_temp)
where min_temp is 62 and max_temp is 68.
The PWM frequency is set ....
2Hz for Speed of 20% to 26%
3Hz for speed of 26% to 32%
4Hz for speed of 32% to 45%
6Hz for speed of 45% to 100%

I have not progressed to PID but I have my doubts its worth it from your comments above and observing what I have so far.

I have used a similar algorithm to control a Sauna Heater and its much easier to get a good result in situations when the load and conditions are constantly changing and super accuracy is not needed.

Whether its worth the trouble or not is debatable but its a nice exercise in Python and control methods.

This snippet shows the core of the method.

if cpu.temp >= max_temp:

speed = 100

elif cpu.temp <= min_temp:

speed = 0


speed = 20 + 80 * (cpu.temp - min_temp)/(max_temp - min_temp)

if speed < 26:

freq = 2

elif speed < 32:

freq = 3

elif speed <= 45:

freq = 4

elif speed <= 100:

freq = 6


speed = 100
freq = 6



Above made in Python3 using a rotating buffer that is sent data on every cycle and only remembers the last 200 sets and then sends an html file here with those last 200 sets of data. Kind of useful for keeping an eye on something. The buffer can also make a csv file so that the data can be more easily analysed at a later date.