### Radio WWV/H Audio Demodulator/Decoder

#### Synopsis

Address: 127.127.36.u
Reference ID: `WVf` or `WHf`
Driver ID: `WWV_AUDIO`
Autotune Port: `/dev/icom`; 1200/9600 baud, 8-bits, no parity
Audio Device: `/dev/audio` and `/dev/audioctl`

#### Description

This driver synchronizes the computer time using data encoded in shortwave radio transmissions from NIST time/frequency stations WWV in Ft. Collins, CO, and WWVH in Kauai, HI. Transmissions are made continuously on 2.5, 5, 10 and 15 MHz from both stations and on 20 MHz from WWV. An ordinary shortwave receiver can be tuned manually to one of these frequencies or, in the case of ICOM receivers, the receiver can be tuned automatically by the driver as propagation conditions change throughout the day and season. The performance of this driver when tracking one of the stations is ordinarily better than 1 ms in time with frequency drift less than 0.1 PPM when not tracking any station.

The demodulation and decoding algorithms used by this driver are based on a machine language program developed for the TAPR DSP93 DSP unit, which uses the TI 320C25 DSP chip. The analysis, design and performance of the program running on this unit is described in: Mills, D.L. A precision radio clock for WWV transmissions. Electrical Engineering Report 97-8-1, University of Delaware, August 1997, 25 pp. Available from www.eecis.udel.edu/~mills/reports.htm. For use in this driver, the original program was rebuilt in the C language and adapted to the NTP driver interface. The algorithms have been modified to improve performance, especially under weak signal conditions and to provide an automatic frequency and station selection feature.

This driver incorporates several features in common with other audio drivers such as described in the Radio CHU Audio Demodulator/Decoder and the IRIG Audio Decoder pages. They include automatic gain control (AGC), selectable audio codec port and signal monitoring capabilities. For a discussion of these common features, as well as a guide to hookup, debugging and monitoring, see the Reference Clock Audio Drivers page.

The WWV signal format is described in NIST Special Publication 432 (Revised 1990). It consists of three elements, a 5-ms, 1000-Hz pulse, which occurs at the beginning of each second, a 800-ms, 1000-Hz pulse, which occurs at the beginning of each minute, and a pulse-width modulated 100-Hz subcarrier for the data bits, one bit per second. The WWVH format is identical, except that the 1000-Hz pulses are sent at 1200 Hz. Each minute encodes nine BCD digits for the time of century plus seven bits for the daylight savings time (DST) indicator, leap warning indicator and DUT1 correction.

#### Program Architecture

As in the original program, the clock discipline is modelled as a Markov process, with probabilistic state transitions corresponding to a conventional clock and the probabilities of received decimal digits. The result is a performance level which results in very high accuracy and reliability, even under conditions when the minute beep of the signal, normally its most prominent feature, can barely be detected by ear using a communications receiver.

The analog audio signal from the shortwave radio is sampled at 8000 Hz and converted to digital representation. The 1000/1200-Hz pulses and 100-Hz subcarrier are first separated using two IIR filters, a 600-Hz bandpass filter centered on 1100 Hz and a 150-Hz lowpass filter. The minute synch pulse is extracted using an 800-ms synchronous matched filter and pulse grooming logic which discriminates between WWV and WWVH signals and noise. The second synch pulse is extracted using a 5-ms FIR matched filter and 8000-stage comb filter.

The phase of the 100-Hz subcarrier relative to the second synch pulse is fixed at the transmitter; however, the audio stage in many radios affects the phase response at 100 Hz in unpredictable ways. The driver adjusts for each radio using two 170-ms synchronous matched filters. The I (in-phase) filter is used to demodulate the subcarrier envelope, while the Q (quadrature-phase) filter is used in a tracking loop to discipline the codec sample clock and thus the demodulator phase.

A bipolar data signal is determined from the matched filter I and Q channels using a pulse-width discriminator. The discriminator samples the I channel at 15 ms (n), 200 ms (s1) and 500 ms (s0), and the envelope (RMS I and Q channels) at 200 ms (e1) and the end of the second (e0). The bipolar data signal is expressed s1 - 2s0 - n. Note that, since the signals s0 and s1 include the noise n, this term cancels out. The data bit SNR is calculated as 20 log10(e1 / e0). If the driver has not synchronized to the minute pulse, or if the data bit amplitude e1 or SNR are below thresholds, the bit is considered invalid and the bipolar signal is forced to zero.

The bipolar signal is exponentially averaged in a set of 60 accumulators, one for each second, to determine the semi-static miscellaneous bits, such as DST indicator, leap second warning and DUT1 correction. In this design a data average value larger than a positive threshold is interpreted as +1 (hit) and a value smaller than a negative threshold as a -1 (miss). Values between the two thresholds, which can occur due to signal fades, are interpreted as an erasure and result in no change of indication.

The BCD digit in each digit position of the timecode is represented as four data bits. The bits are correlated with the bits corresponding to each of the valid decimal digits in this position. If any of the four bits are invalid, the correlated value for all digits in this position is assumed zero. In either case, the values for all digits are exponentially averaged in a likelihood vector associated with this position. The digit associated with the maximum over all averaged values then becomes the maximum likelihood selection for this position and the ratio of the maximum over the next lower value represents the digit SNR.

The decoding matrix contains nine row vectors, one for each digit position. Each row vector includes the maximum likelihood digit, likelihood vector and other related data. The maximum likelihood digit for each of the nine digit positions becomes the maximum likelihood time of the century. A built-in transition function implements a conventional clock with decimal digits that count the minutes, hours, days and years, as corrected for leap seconds and leap years. The counting operation also rotates the likelihood vector corresponding to each digit as it advances. Thus, once the clock is set, each clock digit should correspond to the maximum likelihood digit as transmitted.

Each row of the decoding matrix also includes a compare counter and the most recently determined maximum likelihood digit. If a digit likelihood exceeds the decision level and compares with previous digits for a number of successive minutes in any row, the maximum likelihood digit replaces the clock digit in that row. When this condition is true for all rows and the second epoch has been reliably determined, the clock is set (or verified if it has already been set) and delivers correct time to the integral second. The fraction within the second is derived from the logical master clock, which runs at 8000 Hz and drives all system timing functions.

The logical master clock is derived from the audio codec clock. Its frequency is disciplined by a frequency-lock loop (FLL) which operates independently of the data recovery functions. At averaging intervals determined by the measured jitter, the frequency error is calculated as the difference between the most recent and the current second epoch divided by the interval. The sample clock frequency is then corrected by this amount. When first started, the frequency averaging interval is eight seconds, in order to compensate for intrinsic codec clock frequency offsets up to 125 PPM. Under most conditions, the averaging interval doubles in stages from the initial value to over 1000 seconds, which results in an ultimate frequency precision of 0.125 PPM, or about 11 ms/day.

It is important that the logical clock frequency is stable and accurately determined, since in most applications the shortwave radio will be tuned to a fixed frequency where WWV or WWVH signals are not available throughout the day. In addition, in some parts of the US, especially on the west coast, signals from either or both WWV and WWVH may be available at different times or even at the same time. Since the propagation times from either station are almost always different, each station must be reliably identified before attempting to set the clock.

Reliable station identification requires accurate discrimination between very weak signals in noise and noise alone. The driver very aggresively soaks up every scrap of signal information, but has to be careful to avoid making pseudo-sense of noise alone. The signal quality metric depends on the minute pulse amplitude and SNR measured in second 0 of the minute, together with the data subcarrier amplitude and SNR measured in second 1. If all four values are above defined thresholds a hit is declared, otherwise a miss. The number of hits declared in the last six minutes by each station represents the high order bits of the metric value, while the current minute pulse amplitude repressents the low order bits. The resulting value is then scaled from zero to 100 for use as a quality indicator. It is used by the autotune function described below and reported in the timecode string.

#### Performance

It is the intent of the design that the accuracy and stability of the indicated time be limited only by the characteristics of the ionospheric propagation medium. Conventional wisdom is that synchronization via the HF medium is good only to a millisecond under the best propagation conditions. The performance of the NTP daemon disciplined by the driver is clearly better than this, even under marginal conditions. Ordinarily, with marginal to good signals and a frequency averaging interval of 1024 s, the frequency is stabilized within 0.1 PPM and the time within 0.5 ms. The frequency stability characteristic is highly important, since the clock may have to free-run for several hours before reacquiring the WWV/H signal.

The expected accuracy over a typical day was determined using the DSP93 and an oscilloscope and cesium oscillator calibrated with a GPS receiver. With marginal signals and allowing 15 minutes for initial synchronization and frequency compensation, the time accuracy determined from the WWV/H second synch pulse was reliably within 125 ms. In the particular DSP93 used for program development, the uncorrected CPU clock frequency offset was 45.8±0.1 PPM. Over the first hour after initial synchronization, the clock frequency drifted about 1 PPM as the frequency averaging interval increased to the maximum 1024 s. Once reaching the maximum, the frequency wandered over the day up to 1 PPM, but it is not clear whether this is due to the stability of the DSP93 clock oscillator or the changing height of the ionosphere. Once the frequency had stabilized and after loss of the WWV/H signal, the frequency drift was less than 0.5 PPM, which is equivalent to 1.8 ms/h or 43 ms/d. This resulted in a step phase correction up to several milliseconds when the signal returned.

The measured propagation delay from the WWV transmitter at Boulder, CO, to the receiver at Newark, DE, is 23.5±0.1 ms. This is measured to the peak of the pulse after the second synch comb filter and includes components due to the ionospheric propagation delay, nominally 8.9 ms, communications receiver delay and program delay. The propagation delay can be expected to change about 0.2 ms over the day, as the result of changing ionosphere height. The DSP93 program delay was measured at 5.5 ms, most of which is due to the 400-Hz bandpass filter and 5-ms matched filter. Similar delays can be expected of this driver.

#### Program Operation

The driver begins operation immediately upon startup. It first searches for one or both of the stations WWV and WWVH and attempts to acquire minute synch. This may take some fits and starts, as the driver expects to see several consecutive minutes with good signals and low jitter. If the autotune function is active, the driver will rotate over all five frequencies and both WWV and WWVH stations until at least three good minutes are found.

When a minute synch candidate has been found, the driver acquires second synch, which can take up to several minutes, depending on signal quality. At the same time the driver accumulates likelihood values for the unit (seconds) digit of the nine digits of the timecode, plus the seven miscellaneous bits included in the WWV/H transmission format. When a good unit digit has been found, the driver accumlates likelihood values for the remaining eight digits of the timecode. When three repetitions of all nine digits have decoded correctly, which normally takes 15 minutes with good signals, and up to 40 minutes when buried in noise, and the second synch has been acquired, the clock is set (or verified) and is selectable to discipline the system clock.

Once the clock is set, it continues to provide correct timecodes, even if all signals are losst. The time is considered correct as long as the second synch amplitude and SNR are above specified thresholds and jitter is below threshold. As long as the clock is set or verified, the system clock offsets are provided once each minute to the reference clock interface, where they are processed using the same algorithms used with other local reference clocks and remote servers. Using these algorithms, the system clock can in principle be disciplined to a much finer resolution than the 125-ms sample interval would suggest, although the ultimate accuracy is probably limited by propagation delay variations as the ionspheric height varies throughout the day and night.

The codec clock frequency is disciplined during times when WWV/H signals are available. The algorithm refines the frequency offset using increasingly longer averaging intervals to 1024 s, where the precision is about 0.1 PPM. With good signals, it takes well over two hours to reach this degree of precision; however, it can take many more hours than this in case of marginal signals. Once reaching the limit, the algorithm will follow frequency variations due to temperature fluctuations and ionospheric height variations.

It may happen as the hours progress around the clock that WWV and WWVH signals may appear alone, together or not at all. When the driver has mitigated which station and frequency is best, it sets the reference identifier to the string WVf for WWV and WHf for WWVH, where f is the frequency in megahertz. If the propagation delays have been properly set with the `fudge time1` (WWV) and `fudge time2` (WWVH) commands in the configuration file, handover from one station to the other is seamless.

Once the clock has been set for the first time, it will appear reachable and selectable to discipline the system clock. Operation continues as long as the signal quality from at least one station on at least one frequency is acceptable. A consequence of this design is that, once the clock is set, the time and frequency are disciplined only by the second synch pulse and the clock digits themselves are driven by the clock state machine. If for some reason the state machine drifts to the wrong second, it would never reresynchronize. To protect against this most unlikely situation, if after two days with no signals, the clock is considered unset and resumes the synchronization procedure from the beginning.

However, as long as the clock has once been set correctly and allowed to converge to the intrinsic codec clock frequency, it will continue to read correctly even during the holdover interval, but with increasing dispersion. Assuming the clock frequency can be disciplined within 1 PPM, it can coast without signals for several days without exceeding the NTP step threshold of 128 ms. During such periods the root dispersion increases at 5 ms per second, which makes the driver appear less likely for selection as time goes on. Eventually, when the dispersion due all causes exceeds 1 s, it is no longer suitable for synchronization.

To work well, the driver needs a shortwave receiver with good audio response at 100 Hz. Most shortwave and communications receivers roll off the audio response below 250 Hz, so this can be a problem, especially with receivers using DSP technology, since DSP filters can have very fast rolloff outside the passband. Some DSP transceivers, in particular the ICOM 775, have a programmable low frequency cutoff which can be set as low as 80 Hz. However, this particular radio has a strong low frequency buzz at about 10 Hz which appears in the audio output and can affect data recovery under marginal conditions. Although not tested, it would seem very likely that a cheap shortwave receiver could function just as well as an expensive communications receiver.

#### Autotune

The driver includes provisions to automatically tune the radio in response to changing radio propagation conditions throughout the day and night. The radio interface is compatible with the ICOM CI-V standard, which is a bidirectional serial bus operating at TTL levels. The bus can be connected to a serial port using a level converter such as the CT-17.

Each ICOM radio is assigned a unique 8-bit ID select code, usually expressed in hex format. To activate the CI-V interface, the `mode` keyword of the `server` configuration command specifies a nonzero select code in decimal format. A table of ID select codes for the known ICOM radios is given on the Reference Clock Audio Drivers page. A missing `mode` keyword or a zero argument leaves the interface disabled.

If specified, the driver will attempt to open the device `/dev/icom` and, if successful will activate the autotune function and tune the radio to each operating frequency in turn while attempting to acquire minute synch from either WWV or WWVH. However, the driver is liberal in what it assumes of the configuration. If the `/dev/icom` link is not present or the open fails or the CI-V bus or radio is inoperative, the driver quietly gives up with no harm done.

Once acquiring minute synch, the driver operates as described above to set the clock. However, during seconds 59, 0 and 1 of each minute it tunes the radio to one of the five broadcast frequencies to measure the minute synch pulse amplitude and SNR in second 0 and data pulse amplitude and SNR in second 1 to update the signal metric. In principle, the data pulse in second 58 is usable, but the AGC in most radios is not fast enough for a reliable measurement. Each of the five frequencies are probed in a five-minute rotation to build a database of current propagation conditions for all signals that can be heard at the time. At the end of each probe a mitigation procedure scans the database and retunes the radio to the best frequency and station found. For this to work well, the radio should be set for a fast AGC recovery time. This is most important while tracking a strong signal, which is normally the case, and then probing another frequency, which may have much weaker signals.

At the end of each probe, the frequency and station with the maximum metric is chosen, with ties going first to the highest frequency and then to WWV in order. A station is considered valid only if the metric is above a specified threshold' if below, the rotating probes continue until a valid station is found.

#### Diagnostics

The autotune process produces diagnostic information along with the timecode. This is very useful for evaluating the performance of the algorithms, as well as radio propagation conditions in general. The message is produced once each minute for each frequency in turn after minute synch has been acquired.

`wwv5 status agc epoch secamp/secsnr datamp/datsnr wwv wwvh`

where the fields after the `wwv5` identifier are: `status` contains status bits, `agc` audio gain, `epoch` second epoch, `secamp/secsnr` second pulse ampliture/SNR, and `wwv` and `wwvh` are two sets of fields, one each for WWV and WWVH. Each of the two fields has the format

`ident score metric minamp/minsnr`

where `ident` encodes the station (`WV` for WWV, `WH` for WWVH) and frequency (2, 5, 10, 15 or 20), `score` 32-bit shift register recording the hits (1) and misses (0) of the last 32 probes (hits and misses enter from the right), `metric` is described above, and `minamp/minsnr` minute pulse ampliture/SNR. An example is:

`wwv5 000d 111 5753 3967/20.1 3523/10.2 WV20 bdeff 100 8348/30.0 WH20 0000 1 22/-12.4`

There are several other messages that can occur; these are documented in the source listing.

#### Debugging Aids

The most convenient way to track the driver status is using the `ntpq` program and the `clockvar` command. This displays the last determined timecode and related status and error counters, even when the driver is not disciplining the system clock. If the debugging trace feature (`-d` on the `ntpd` command line)is enabled, the driver produces detailed status messages as it operates. If the `fudge flag 4` is set, these messages are written to the `clockstats` file. All messages produced by this driver have the prefix `wwv` for convenient filtering with the Unix `grep` command.

#### Monitor Data

When enabled by the `filegen` facility, every received timecode is written to the `clockstats` file in the following format:

`sq yyyy ddd hh:mm:ss ld du lset agc ident metric errs freq avg
s` synch indicator (`?` or space) `q` quality character (see below) `yyyy` Gregorian year `ddd` day of year `hh` hour of day `mm` minute of hour `l` leap second warning `L` `d` DST state `S, D, I, O`
`dut` DUT sign and magnitude `lset` minutes since last set `agc` audio gain `ident` station identifier and frequency `metric` signal metric (0-100) `errs` data bit errors in last minute `freq` codec frequency offset (PPM) `avg` frequency averaging interval (s)

The fields beginning with `year` and extending through `dut` are decoded from the received data and are in fixed-length format. The `agc` and `lset` fields, as well as the following driver-dependent fields, are in variable-length format.

`s`
  The synch indicator is initially `?` before the clock is set, but turns to space when all nine digits of the timecode are correctly set and the decoder is synchronized to the station within 125 ms.
`q`
  The quality character is a four-bit hexadecimal code showing which alarms have been raised. Each bit is associated with a specific alarm condition according to the following:
  `0x8`
    synch alarm. The decoder is not synchronized to the station within 125 ms.
  `0x4`
    Digit error alarm. Less than nine decimal digits were found in the last minute.
  `0x2`
    Error alarm. More than 40 data bit errors were found in the last minute.
  `0x1`
    Compare alarm. A maximum likelihood digit failed to agree with the current associated clock digit in the last minute.
  It is important to note that one or more of the above alarms does not necessarily indicate a clock error, but only that the decoder has detected a condition that may result in an error. However, the local clock update is not suppressed if any alarm bits are set other than a synch alarm.
`yyyy ddd hh:mm:ss`
  The timecode format itself is self explanatory. Since the driver latches the on-time epoch directly from the second synch pulse, the seconds fraction is always zero. Although the transmitted timecode includes only the year of century, the Gregorian year is augmented by 2000.
`l`
  The leap second warning is normally space, but changes to `L` if a leap second is to occur at the end of the month of June or December.
`d`
  The DST state is `S` or `D` when standard time or daylight time is in effect, respectively. The state is `I` or `O` when daylight time is about to go into effect or out of effect, respectively.
`dut`
  The DUT sign and magnitude shows the current UT1 offset relative to the displayed UTC time, in deciseconds.
`lset`
  Before the clock is set, the interval since last set is the number of minutes since the driver was started; after the clock is set, this is number of minutes since the decoder was last synchronized to the station within 125 ms.
`agc`
  The audio gain shows the current codec gain setting in the range 0 to 255. Ordinarily, the receiver audio gain control should be set for a value midway in this range.
`ident`
  The station identifier shows the station, `WVf` for WWV or `WHf` for WWVH, and frequency `f` being tracked. If neither station is heard on any frequency, the reference identifier shows `NONE`.
`metric`
  The signal metric described above from 0 (no signal) to 100 (best).
`errs`
  The bit error counter is useful to determine the quality of the data signal received in the most recent minute. It is normal to drop a couple of data bits under good signal conditions and increasing numbers as conditions worsen. While the decoder performs moderately well even with half the bits are in error in any minute, usually by that point the metric drops below threshold and the decoder switches to a different frequency.
`freq`
  The frequency offset is the current estimate of the codec frequency offset to within 0.1 PPM. This may wander a bit over the day due to local temperature fluctuations and propagation conditions.
`avgt`
  The averaging time is the interval between frequency updates in powers of two to a maximum of 1024 s. Attainment of the maximum indicates the driver is operating at the best possible resolution in time and frequency.

An example timecode is:

`0 2000 006 22:36:00 S +3 1 115 WV20 86 5 66.4 1024`

Here the clock has been set and no alarms are raised. The year, day and time are displayed along with no leap warning, standard time and DUT +0.3 s. The clock was set on the last minute, the AGC is safely in the middle ot the range 0-255, and the receiver is tracking WWV on 20 MHz. Good receiving conditions prevail, as indicated by the metric 86 and 5 bit errors during the last minute. The current frequency is 66.4 PPM and the averaging interval is 1024 s, indicating the maximum precision available.

#### Fudge Factors

`time1 time`
  Specifies the propagation delay for WWV (40:40:49.0N 105:02:27.0W), in seconds and fraction, with default 0.0.
`time2 time`
  Specifies the propagation delay for WWVH (21:59:26.0N 159:46:00.0W), in seconds and fraction, with default 0.0.
`stratum number`
  Specifies the driver stratum, in decimal from 0 to 15, with default 0.
`refid string`
  Ordinarily, this field specifies the driver reference identifier; however, the driver sets the reference identifier automatically as described above.
`flag1 0 | 1`
  Not used by this driver.
`flag2 0 | 1`
  Specifies the microphone port if set to zero or the line-in port if set to one. It does not seem useful to specify the compact disc player port.
`flag3 0 | 1`
  Enables audio monitoring of the input signal. For this purpose, the speaker volume must be set before the driver is started.
`flag4 0 | 1`
  Enable verbose `clockstats` recording if set.