[GPS_Standard] Proportional and/or integral adjustment

Dave Platt dplatt at radagast.org
Tue May 25 17:03:28 EDT 2010


In looking at the design, and code, and behavior of the
current controller firmware, I had an idea which might
allow for greater flexibility and accuracy in the
oscillator tracking, without requiring too much effort
to implement.

Currently, the controller has only two quanta of adjustment
for the DAC:  fine, and coarse (the latter being 16x the
former), with a single error threshold being used to select
between the two (and lower "negation" threshold being used to
suppress any change at all).  This allows the correction
increment to be proportional to the amount of error... but
only roughly so.  There's no way to get an intermediate
correction step, or one larger than the "coarse" step...
the effect of both can be achieved by making more frequent
corrections (shorter averaging period) but as you've noted
this comes at the expense of greater jitter sensitivity and
thus reduced accuracy.

In looking at the tracking reports from my controller, I
notice a pattern during periods of temperature change:

   F+ F+ C+ F+ F- F+ C+ F- F+ F+ F+ C+

or something of that sort... the controller is fairly
consistently changing the control voltage in the same
direction, and is alternating between "fine" and "coarse"
adjustments.  Apparently, the desired rate-of-change is
averages out to somewhere between "fine" and "coarse", and
the controller is forced to dither between these two adjustments
to create the correct average.  This would lead to poorer accuracy,
over this period, than would be the case if the adjustments were
made at the ideal step sizes (somewhere between coarse and fine).

It seems to me that it might be possible to change the logic
a bit, by redefining turning the "fine threshold" parameter
into a "fine/coarse scaling" value.  Currently, the logic
has the effect of (something like):

  if |error| < negate then
    correction = 0
  else if |error| < fine then
    correction = 1 * sign(error)
  else
    correction = 16 * sign(error)

The revision would be along the lines of

  if |error| < negate then
    correction = 0
  else
    correction = (error * fine) / 4 [with logic to handle overflows
                                     by setting "correction" to the
                                     maximum reasonable step]

In other words, the "fine" value would act as a scaled
proportion.  A value of "8", for example, would have the
effect of meaning that a 2-count error in the sample would
result in a voltage correction of 4 finesteps (or 1/4
coarsestep).  A value of "2" would mean that a 2-count error
would result in a 1-finestep adjustment.

[I chose the scaling value of 4 - i.e. a 2-bit right signed
 shift - out of a hat.  Larger values such as 8 or 16 would
 allow for more precision in setting the proportion, but would
 tend to limit the maximum correction step.]

This sort of change might allow for more rapid initial
acquisition during initial turn-on - rather than having to reduce
the sample averaging period, you could just make larger adjustments
after each individual period.  It could also allow for better
accuracy during steady-state operation, by reducing the number
of unnecessarily-large "coarse" adjustments.

On many micros, this might be too expensive/bothersome to
implement... but it looks as if the PIC18F2220 has a reasonably
decent hardware multiplier which might be used to do the
multiply quite quickly, and the divide-by-4 would be a
two-byte signed right shift.

Another tweak would be to an an "error integral" to the
calculation... keep some sort of scaled or IIR-filtered
sum of the accumulated errors over the last N averaging
intervals, clip this value to some |maximum| to avoid
excessive-windup problems, scale it, and add it to the
correction value as calculated above.  This would allow the
controller to start making even larger adjustments when it's
consistently fast or consistently slow.  This would come
at the cost of some additional code complexity, and
(depending on the "fine scaling" and "integral scaling"
factors) there could be some overshoot.

Comments?  Suggestions?  Dirty remarks?

This is a *really* fun little project - Bert, thanks
immensely for developing and publishing it!

73,

	Dave AE6EO


More information about the GPS_Standard mailing list