On Sat, Aug 15, 2020 at 09:10:26AM +0100, Julian Smith wrote:
> On Mon, 10 Aug 2020 09:53:10 +0200
> Otto Moerbeek <[email protected]> wrote:
>
> > On Sun, Aug 09, 2020 at 09:46:00PM +0100, Julian Smith wrote:
> >
> > > I've just used adjfreq() directly to correct my hardware clock,
> > > which was running an hour ahead of UTC (due to my hardware
> > > previously running Windows).
> > >
> > > But i've struggled to understand the adjfreq(2) man page, so ended
> > > up finding a value for <freq> by trial and error.
> > >
> > > I ended up with this code:
> > >
> > > double x = 1.5;
> > > int64_t newfreq = ((1ll << 32) * 1e9) * x;
> > > adjfreq(newfreq, NULL);
> >
> > This does not look like actual code, first arg should be a pointer.
>
> Ah yes, apologies for this, i foolishly hand-wrote the code above in
> the post. The actual code i used did pass a pointer:
>
> e = adjfreq(&newfreq, &oldfreq);
>
> >
> > >
> > > In this table, the second column is the increment in the time as
> > > shown by running date(1) twice, over a 10 second period as measured
> > > using my phone as a timer, for different values of x:
> > >
> > > x 10s
> > > -------------
> > > 0 10
> > > 0.1 12
> > > 0.25 13
> > > 0.5 15
> > > 0.75 17
> > > 0.8 19
> > > 0.9 19
> > > 1.0 21
> > > 1.1 1
> > > 1.25: 3
> > > 1.5: 6
> > > 1.75: 8
> > > 2: 10
> > > 2.25: 10
> > > 2.5: 10
> >
> > The only user of adjfreq(2) in base is ntpd(8), which caps it's
> > adjustments between +/-MAX_FREQUENCY_ADJUST = 128e-5.
> >
> > It is very well possible the calculations in the kernel go wrong with
> > large(r) values. The API exists for gradual adjustments, not for
> > anything big. Scott Cheloha <[email protected]> has been working
> > on the kernel side of things, he might know more, so I Cc'ed him,
> > don't know if her reads misc@.
>
> Thanks for doing this.
>
> Using a big adjustment was very convenient for fixing my problem, so it
> might be of general use/interest. I guess alternatives would be to get
> control early in boot and fix it up; or i think one can tell the OS that
> the hardware clock is set to a particular offset from UTC (can't find
> the man page for this right now, but i'm sure i came across it when
> investigating adjfreq).
ntpd fixes the clock very early in the boot using both htpps and ntp
time sources, but is conservative: it does not do backward
adjustments. There is utc_offset in src/conf/param.c.
-Otto