PWM control of small fans
ManAtWork
Posts: 2,176
in Propeller 2
I'm experimenting with control of the speed of a small brushless fan like the ones used in PCs or power supplies. A propeller pin drives the base of a small NPN transistor. The code is quite easy:
However, I'm not so happy with the audible noise generated. The fan runs best with frequencies between 200 and 1000Hz but this causes some whistling. At higher frequencies the sound is softer but the speed vs. PWM duty response gets nonlinear and and the motor has startup problems at low speed.
I guess this is caused by the cheap commutation circuit in the brushless motor. Although I have a free-wheeling diode in my driver it doesn't work really well. So the current drops to zero (fast decay) in each off-phase of the transistor and the winding inductance limits the current rise in the next on-phase.
Does anybody know how fan speed control works in PCs? They run almost quiet. Running the fan from a linear regulator (lab power supply) works much better than PWM but a linear regulator dissipates heat. A switch mode regulator with filtered DC output costs money and both solutions require much more board space than a simple transistor.
CON pwmFreq = 500 pwmFrame = 240 ' 24V in 0.1V units pwmBase = freqPll / (pwmFreq * pwmFrame) PUB InitFanPwm asm fltl #pinFan wrpin #%01_01001_0,#pinFan wxpin ##pwmFrame<<16+pwmBase,#pinFan drvl #pinFan endasm PUB SetFanVolt (v) ' set fan PWM in 0.1V units asm wypin v,#pinFan endasm
However, I'm not so happy with the audible noise generated. The fan runs best with frequencies between 200 and 1000Hz but this causes some whistling. At higher frequencies the sound is softer but the speed vs. PWM duty response gets nonlinear and and the motor has startup problems at low speed.
I guess this is caused by the cheap commutation circuit in the brushless motor. Although I have a free-wheeling diode in my driver it doesn't work really well. So the current drops to zero (fast decay) in each off-phase of the transistor and the winding inductance limits the current rise in the next on-phase.
Does anybody know how fan speed control works in PCs? They run almost quiet. Running the fan from a linear regulator (lab power supply) works much better than PWM but a linear regulator dissipates heat. A switch mode regulator with filtered DC output costs money and both solutions require much more board space than a simple transistor.
Comments
You could try using DAC mode (990 ohm) that changes only to set the speed. If you are using an NPN, you might get a good linear range by driving the DAC pin right into the base.
Also, try the PWM mode, as is, but with 1.5k-ohm drive mode on the pin.
I could build something that behaves more like a voltage amplifier by adding a feedback resistor between C and B. However, for a linear amplifier I'd need a much bigger transistor because of the heat generated. 24V * 0.2A = 4.8W half of it (= 2.4W) would be dissipated by the transistor in worst case. This required at least a DPAK. Currently I'm using a small SOT-23 one.
BTW, I'm not sure if I've understood how the resistor modes of the P2 pins work. Those are series resistors, correct? So if I want an open collector driver with pullup I have to actively drive the pin high with series resistor instead of letting it float with pullup, right?
A good cost vs. performace compromise might be a pulse-density NCO output driving a small high-speed MOSFET + free-wheeling diode and an LC filter to smoothen the output. This way the fan would see nearly DC and noise would be reduced.
The resistors are on the chip. There are two three-bit selector fields for what kind of impedance you want for both high and low outputs. You could make low float (LLL = %111) and high drive via a 1.5k resistor (HHH = %001).
I'm working on the documentation for this now, so that I can get some constant symbols into the Spin2 compiler.
I've done a quick simulation. A filter with a 10µH inductor and 100nF cap is enough to limit voltage ripple to 1V at 1MHz. However, current ripple would be quite large (0.4A). 22µH and 1µF gives much better results.
Unfortunatelly I have to use 24V fans and speed signal is not available for most of them. An additional 12V regulator only for the fan is too expensive. Ok, I could roll my own with PWM output from the P2 and voltage feedback via an ADC pin, but that's also overkill.
I'll try out the LC filter solution tomorrow. I found out that I only have MOSFETs that are either rated only for 20V or have a gate threshold of >4.5V and can't be driven directly by a P2 pin.
So it doesn't matter much if the speed of the fan is exactly proportional to the PWM duty cycle. The control loop will self adjust. But it makes a bad impression if the fan is whisteling and humming without actually running.
Pretty cool.
It surely also works with 12V. Just replace the 240 with 120.
I think your original drawing is buried in some obscure thread that can't be easily searched.
It surely sounds interesting and maybe it could be used to implement a PFC stage, later.
I found this description
https://forums.parallax.com/discussion/comment/1362413/#Comment_1362413
Of course there is ripple on the DC bus. Low frequency ripple (100 or 120Hz) is quite high (~50V) but is suppressed by measuring the bus voltage and applying an inverse feed forward to the PWM ratio.
Fan PWM and internal DC/DC-converters work at frequencies well above the pass-band of all ADC input filters.
And yes, the internal circuits in the BLDC fans are really bad. It's just a hall sensor based block commutation logic. But the winding resistance is so high that it doesn't hurt.
There are quite a few step down switching regulator chips available that would be suitable, and they are not much harder to deal with than a typical linear regulator. Take a look at this data sheet. I'm not suggesting you use that particular one, it just happened to come up near the top of the list. it is a bit pricey, but there are several for under $1.00. There are also TO220 sized modules available.
I tried your code in flexgui. Got an error. Did I miss something??
Found your project interesting.
Thanks
Martin
"C:/Users/bsa/Desktop/flexgui 4.0.3/flexgui/flexgui/bin/fastspin" -2b -l -O1 -I "C:/Users/bsa/Desktop/flexgui 4.0.3/flexgui/flexgui/include" "C:/Users/bsa/Desktop/parallax/PROP_2/SMPART PINS/man at work/pwm brushless motor.spin"
Propeller Spin/PASM Compiler 'FastSpin' (c) 2011-2019 Total Spectrum Software Inc.
Version 4.0.3 Compiled on: Nov 9 2019
pwm brushless motor.spin
C:/Users/bsa/Desktop/parallax/PROP_2/SMPART PINS/man at work/pwm brushless motor.spin:5: error: Unknown symbol pllfreq
child process exited abnormally
Finished at Sat Mar 21 14:16:11 2020
You appear to be running a fairly old release of flexgui. If you updated to the latest it would probably fix your issue.
Simply replace "pllfreq" with your system clock frequency. I've defined it because "clkfreq" can't be used in constant expresssions.
@ManAtWork
I will try that, thanks.