Rewiring and updating channels
I just re configured the heater driver to the configuration C illustrated in the last post.
When I actually opened up the sub-D15 connector I found the previous configuration was not what I thought it was. The actual wiring was optimally bad, see attached schematic. The resister network paralleled 38 Ω and 70 Ω heater blocks and then puts those pairs in series. This meant uneven heating and higher resistance.
I've rewired to put all heaters in parallel and updated the IOC db file entry for the heater voltage channel to max out at 1.5 V (1.5A at output). We should make a point of putting fuses in the heater driver circuits soon, to prevent a meltdown from mistakes in input voltage: this is now a going concern with the low heater impedance. And/or implement a zenor diode crimp at the input.
Issue with high current affecting temperature readout
I ramped the drive current all the way up to 1.5 A, this is 27.7 W. This was max 9.7 W max before. The out-of-loop sensor showed an immediate rise in temperature climbing at 0.16 K/min; the can can get from room temperature to 30 C in 1h20min which is much better than the 4-6 hours before.
However, I noticed when I cycled the current up and down this changed the reported temperature (in the out of loop sensor!). Which is very bad. The transimpedance temperature sensor box that converts AD590 1µV/K sensor current to voltage runs off the same 24V lines as the heater. However, this voltage is regulated down to 12 V (pretty sure) and should be well bypassed on the board. So I'm not sure what the interaction is here. There should be a wide margin for the sensor board voltage regulators and the AD590 should also be pretty immune to any voltage dip (if there is one).
The temperature sensor board is reporting a full 0.6 degrees below when the heater driver is turned all the way up. This needs to be debugged pronto in case all our temperature readouts are bogus.
Issue with the PID
Another issue I found was with the PID. I don't think this is related to the above temperature dip with heater drive current changes. The PID (settings P = -0.50, I = 0.00020, D = 0) was actually reducing the current drive to 0.700 A when started from 1.5 A, even 5 K below the set point. It should slowly wind up to the actuator limit and stay there until the set point is exceeded. I have two theories:
- that the high value of P and the upper current limit have a ratcheting effect: upward movements in current hit an upper bound and the finite difference approximation used by the PID python locker subtracts the previous iteration's value. This onesidedness effectively creates a negative integration term (in the wrong direction) pulling the process value down; and
- there is an issue with the finite difference approximation of the PID loop itself, due to rounding errors. We only really need a small integration term to push the temperature to set point. The chosen value mainly determines how fast the can comes to temperature*. Setting it too high ends up with integrator wind up and oscillating overshoot. I wonder if implementing a finite difference version of the PID introduces accumulated rounding errors when the P and I terms are very different magnitude. A different implementation of the loop would keep computation of P, I and D separate until the last step of summing them all together. In that scheme one would only accumulate value on the integration term, avoiding many add subtract operations that may round the last digit off a much smaller integrator compared to other terms.
I turned down the P term and this seemed to solve the problem, but it shouldn't do this in the first place. I've had a suspicion for a while that adjusting the P value was actually introducing an integration affect (usually in the opposite sign to the integrator term). However, it wasn't this extreme in previous cases.
This python PID script is a direct port of an earlier Perl script used at the 40m. Its a very Perly way of solving the problem: using a single vector each for the process and error and performing shifting and pop on that vector. A python noob might write a script more like that given on Wikipedia.
Changing the script isn't a lot of work, but working out what is wrong and why might be harder.
*it will also effect the bandwidth of the loop I guess.
For the vacuum can heater, we are limited in the heater driver max power by the positive supply rail voltage and the maximum current permissible through the sense resistor. The 54 Ω of the can heater means that for 0.44 A of drive current, the drop across the heater is 24 V, the maximum voltage available to the circuit. Thus there is a limit to total heating of 9.77 W, accounting for sense resistor and MOSFET voltage drop.
...For now I will just configure the heaters to all be in parallel (configuration C)...