Tuning LinuxCNC/HAL PID loops
Tuning is a difficult topic. Everybody has their own preferred way to do it, and each way has its good and bad points.
There is usually a lot of trial and error involved. Experience and intuition both help, but both are very hard to explain
This page is a spot for various LinuxCNC users to describe their individual approaches to tuning, and to share hints and tips.
Please add any thoughts you have on the subject. Put your name in front of your comments.
Starting from scratch:
I tend to take a "bottom up" approach to building things. I don't even start with LinuxCNC at all, I just build single axis position loops with HAL and test them with input signals from a signal generator. Only when the position loops work do I connect them to LinuxCNC itself. This is probably NOT the way most folks want to do things, I do it this way because I am very comfortable with HAL. Someday (when I get around to it) I might make .hal files and instructions that would walk unexperienced HAL users thru my methods, but right now I only have time to describe things in general terms.
(Note - I use inches for everything here, because I really don't feel like typing "inches (or mm)" a dozen times. Wherever you see "inches" in this document, you can assume "(or mm)" follows it. You can actually can use any machine units you want, as long as you are consistent. The units used for all the HAL blocks are the same as the units defined in the LinuxCNC ini file. If you are really perverse, you could use furlongs, but most folks use either inches or mm.)
Step by step for a new machine
- Get the encoder(s) working.
- Any servo system needs position feedback. Most systems use a quadrature encoder on the motor for feedback. You need to get the hardware working first - encoder wiring, encoder power, connections to whatever hardware or software device you intend to use to count the encoder pulses. Details for that depends on the devices. Once the hardware is set up, your HAL file needs to load the appropriate driver(s) for your hardware (and also load the software encoder counter HAL module if you are using that). Details later. With the motor power turned off you should be able to turn the motor shaft and see the encoder "counts" parameter change using "halcmd show param" or halmeter.
- Set encoder scale
- Use the machine data to calculate the number of encoder counts per inch (or mm). For example, if your machine has 5 turn per inch ballscrews, a 40 tooth timing belt pulley on the leadscrew, a 20 tooth pulley on the motor, and a 512 cycle per revolution (2048 count per revolution) encoder, the scale is 5 turns per inch * ( 40 teeth on screw / 20 teeth on motor ) * 2048 counts/rev = 20480 counts per inch. The position-scale parameter of the encoder HAL block should therefore be 20480. Once you set the scale parameter, then the 'position' HAL pin shows the axis position in inches (or mm).
- Verify encoder polarity
- With the motor power turned off manually turn each axis so that the machine moves in the positive direction (whatever you want that to be on your machine). If the reported encoder position increases, polarity is correct and you can go to the next step. If the reported position decreases, the polarity is reversed. This can be dealt with two ways. You can fix the hardware so it counts the right way (for example, swap A and B encoder signals, or swap A and A-not on a differential encoder). Or you can fix it in software, by setting the scale to a negative value. The choice is a matter of personal preference. I like to keep the wiring for all axes the same (to avoid confusion later if someone is servicing the machine) so I would probabaly use negative scale values.
- Rough verify encoder scale
- With the motor power turned off write down the value of the 'position' HAL pin, then manually turn the axis so that the machine moves a known distance, for example one inch. Then write down the new value of the 'position' HAL pin, and subtract the two readings. The difference should be the distance you moved the machine (one inch, or whatever). If it is off by a few percent that is no problem, it can be fine tuned later. If it is off by a lot, go back to the step where you calculated the scale, figure out what went wrong, and fix it. Once the position feedback accurately (within a few percent) indicates the actual movement of the axis (both scale and direction) go to the next step.
- Velocity or Torque mode?
- A servo system can run in one of two modes, based on the meaning of the command signal to the servo amps. If the amp signal represents the desired motor torque, the system is in torque mode. If the signal to the amp represents the desired motor speed, the system is in velocity mode. (Note: with brush DC motors, torque is proportional to armature current, and velocity is proportional to armature voltage. So if the amp input controls the output current, your system is torque mode. If the amp input controls the output voltage, your system is in velocity mode. These steps are primarily for velocity mode, the tuning parameters and approach will be different for torque mode.
- Addition from jros (not an expert): I think that some of the non-standard PID module tuning parameters like FF0, FF1, FF2 and bias, have more sense if in torque mode, because they tend to represent a physical estimation of a priori needed torque (i.e.: FF1 viscous, FF2 inertial, bias gravity,...). I can not figure out FF1 meaning -for example- if controlling in velocity mode.
- Verify DAC outputs
- Connect a HAL signal to the DAC outputs, set the DAC scaling set to 1.0. Then with motor/amp power off, set the HAL signal to 1.0 volts and verify (with a meter) that the output is correct. Repeat with -1.0 volts. Then verify with larger values, depending on the range of the DAC, for example 5.0 volts, and -5.0 volts.
The following steps need more detail, but I'm out of time tonight.
- Set DAC scaling
- calculate based on volts/RPM, etc, so that the HAL DAC pin is scaled in inches/second.
- Verify amp polarity and scale
- Command a slow open-loop move by setting DAC output to 0.05 inches/sec or so and verify that the actual axis speed and direction are correct. Speed errors of 10-20% or so are OK, but reversed polarity or gross speed errors need fixed.
- Set up PID loop
- add the loop and interconnect
- Set up test signal
- HAL stuff, multiple ways to do...
more steps to follow...
Some Articles On Tuning