I’ve had a couple questions about what’s different between my demo5 code and the 2.4.3 release code. Here’s a list of what I think are the significant differences. Any changes that I have made but have then been ported back to the release code are not included here.
After describing my simple Pi based data logger in my last post, I stumbled across this Raspberry Pi based GPS project on diydrones.com. It uses an M8T receiver and includes a touchscreen GUI to manage RTKLIB. It has downloadable files for 3D printing the case as well as an image file with all the code for the SD card (something I should probably provide with mine).
I haven’t looked at in great detail but it seems very intriguing and could be a good alternative to what I described in my last post if you are looking for something with greater capability.
Here’s a photo of the completed project.
One of the nice things about RTKLIB is that it is extremely configurable and has a whole slew of input options available. Unfortunately these can be a bit overwhelming at times, especially for someone new to the program. The RTKLIB manual does briefly explain what each option does, but even with this information it can be difficult to know how best to choose values for some of the parameters.
I won't try to give a comprehensive explanation of all the input options here, but will explain the ones I have found useful to adjust in my experiments and include a little about why I chose the values I did. I describe them as they appear in the configuration file rather than how they appear in the RTKNAVI GUI menu but the comments apply to both. I created this list by comparing my latest config files to the default config file and noting which settings were different. The values in the list below are the values I use in my config file for a 5 Hz rover measurement rate. The same config files can be used for either RTKNAVI, RTKPOST, or RNX2RTKP.
The settings and options highlighted in blue below are available only in my demo code and not in the release code but otherwise much of what I describe below will apply to either code. Most of my work is done with Ublox M8N and M8T receivers with short baselines and these settings will more directly apply to those combinations but should be useful at least as a starting point for other scenarios.
pos1-posmode = static, kinematic, static-start, movingbase, fixed
If the rover is stationary, use “static”. If it is moving, “kinematic” or “static-start”. I always require the rover to be stationary long enough to get first fix, in which case “static-start” usually works better because it take advantage of the knowledge that the rover is not moving initially. Use “movingbase” if the base is moving as well as the rover. In this case be sure to set “pos2-baselen” and “pos2-basesig” as well. Use “fixed” if you know the rover's exact location and are only interested in analyzing the residuals.
pos1-frequency = l1
All my receivers are single frequency so I turn off L2
pos1-soltype = forward, backward, combined
This is the direction in time that the kalman filter is run. “Combined” combines the result of forward and backward. For real-time processing, “forward” is your only choice. “Combined” will often give a better solution than “forward” for post-processed data but I don't use it much since I am more interested in solutions that will work for either real-time or post-process. The kalman filter will have to acquire in both directions, so you will need the rover to be stationary for a period of time at the end of your data as well as the beginning, especially if you are using “static-start” mode. I sometimes use the “backward” setting for debug when I am having trouble getting an initial fix and want to know what the correct satellite phase-biases are.
pos1-dynamics = on
Enabling rover dynamics adds velocity and acceleration states to the kalman filter for the rover. It will improve “kinematic” and “static-start” results, but will have little or no effect on “static” mode. The release code will run noticeably slower with dynamics enabled. Be sure to set “prnaccelh” and “prnaccelv” appropriately for your rover acceleration characteristics.
pos1-navsys = 7
I always include GLONASS and SBAS sats, as more information is generally better.
pos2-armode = fix-and-hold, continuous
Integer ambiguity resolution method. I almost always use "fix-and-hold" because I find it is difficult to get robust solutions with low cost receivers, at least for moving rovers, without it. Be careful though, “fix-and-hold” can cause more false fixes than “continuous” and will hold them longer. I will sometimes use “continuous” for static data sets. If “armode” is not set to “fix-and-hold” then any of the options below that refer to holds don't apply, including gloarmode.
pos2-gloarmode = on, fix-and-hold
Integer ambiguity resolution for the GLONASS sats. If your recievers are identical, you can usually set this to “on” which is the preferred setting since it will allow the GLONASS sats to be used for integer ambiguity resolution during the initial acquire. If your receivers are different or you are using two Ublox M8N receivers you will need to calibrate the inter-channel biases with the “fix-and-hold” setting. In this case the GLONASS sats will not be used for inter-channel ambiguity resolution until after they have been calibrated which begins after the first hold.
pos2-arfilter = on
Setting this to on will qualify new sats or sats recovering from a cycle-slip. If a sat significantly degrades the AR ratio when it is first added, its use for ambiguity resolution will be delayed. Turning this on should allow you to reduce “arlockcnt” which serves a similar purpose but with a blind delay count.
pos2-arthres1 = 0.004
Integer ambiguity resolution is delayed until the variance of the position state has reached this threshold. It is intended to avoid false fixes before the kalman filter has had time to converge. If you see AR ratios of zero extending too far into your solution, you may need to increase this value. The “arthres1” option exists in the release code config file but is not used for anything.
pos2-arlockcnt = 75 (15*sample rate)
Number of samples to delay a new sat or sat recovering from a cycle-slip before using it for integer ambiguity resolution. Avoids corruption of the AR ratio from including a sat that hasn't had time to converge yet. Use in conjunction with “arfilter”. Note that the units are in samples, not units of time, so it must be adjusted if you change the rover measurement rate.
pos2-minfixsats = 3
Minimum number of sats necessary to get a fix. Used to avoid false fixes from a very small number of satellites, especially during periods of frequent cycle-slips.
pos2-minholdsats = 5
Minimum number of sats necessary to hold an integer ambiguity result. Used to avoid false holds from a very small number of satellites, especially during periods of frequent cycle-slips.
pos2-arelmask = 15
Functionally no different from the default of zero, since elevations less than “elmask” will not be used for ambiguity resolution but I changed it to avoid confusion.
pos2-arminfix = 100 (20*sample rate)
Number of consecutive fix samples needed to hold the ambiguities. Increasing this is probably the most effective way to reduce false holds, but will also increase time to first hold. Note that this value also needs to be adjusted if the rover measurement rate changes.
pos2-elmaskhold = 15
Functionally no different from the default of zero, since elevations less than “elmask” will not be used for holding ambiguity resolution results but I changed it to avoid confusion.
pos2-aroutcnt = 100 (20*sample rate)
Number of consecutive missing samples that will cause the ambiguities to be reset. Again, this value needs to be adjusted if the rover measurement rate changes.
pos2-maxage = 100
Maximum delay between rover measurement and base measurement (age of differential) in seconds. This usually occurs because of missing measurements from a misbehaving radio link. I've increased it from the default because I found I was often still getting good results even when this value got fairly large, assuming the dropout occurred after first fix-and-hold.
pos2-rejionno = 1000
Reject a measurement if its pre-fit residual is greater than this value in meters. I have found that RTKLIB does not handle outlier measurements well, so I set this large enough to effectively disable it. There was a recent bug fix in the release code related to outliers but even with this fix I found that I got better results with a larger value.
out-solformat = enu, llh
I am usually interested in relative distances between rover and base, so set this to “enu”. If you are interested in absolute locations, set this to “llh” but make sure you set the exact base location in the “ant2” settings.
out-outhead = on
No functional difference to the solution, just output more info to the result file.
out-outopt = on
No functional difference to the solution, just output more info to the result file.
out-outstat = residual
No functional difference to the solution, just output residuals to a file. The residuals can be very useful for debugging problems with a solution.
stats-eratio1 = 300
Ratio of the standard deviations of the pseudorange measurements to the carrier-phase measurements. I have found a larger value works better for low-cost receivers, but that the default value of 100 works better for more expensive receivers. Actually measuring the residuals is not hard and I have planned on doing that for a long time but have still not got around to it. Larger values tend to cause the kalman filter to converge faster and leads to faster first fixes although it is possible it also increases the chance of a false fix. If you change this value, you may also need to change the “pos2-arthres1” value.
stats-prnaccelh = 1.0
If receiver dynamics are enabled, use this value to set the standard deviation of the rover receiver acceleration in the horizontal components. This value should include accelerations at all frequencies, not just low frequencies. It should characterize any movements of the rover antenna, not just movements of the complete rover so it may be larger than you think. It will include accelerations from vibration, bumps in the road, etc as well as the more obvious rigid-body accelerations of the whole rover.
stats-prnaccelv = 0.25
The comments about horizontal accelerations apply even more to the vertical acceleration component since in many applications the intentional accelerations will all be in the horizontal components. It is best to derive this value from actual GPS measurement data rather than expectations of the rigid-body rover. It is better to over-estimate these values than to under-estimate them.
ant2-postype = rinexhead, llh, single
This is the location of the base station antenna. If you are only interested in relative distance between base and rover this value does not need to be particularly accurate. For post-processing I usually use the approximate base station location from the RINEX file header. If you want absolute position in your solution, then the base station location must be much more accurate since any error in that will add to your rover position error. If I want absolute position, I first process the base station data against a nearby reference station to get the exact location, then use the ”llh” option to specify that location. For real-time processing, I use the “single” option which uses the single solution from the data to get a rough estimate of base station location.
ant2-maxaveep = 1
Only used for real-time processing. Specifies the number of samples averaged to determine base station location if “postype” is set to “single”. I set this to one to prevent the base station position from varying after the kalman filter has started to converge since that seems to cause long times to first fix.
Please help me update this list if you have had success adjusting other options or using different settings for these options, or if you disagree with any of my suggestions. I will treat this as a working document and continue to update it as I learn more.