以编程方式检测 Chrony 时间同步事件

以编程方式检测 Chrony 时间同步事件

我正在开发一个传感器系统,该系统运行在嵌入式 Linux 平台上,无法访问互联网。连接外部 GPS 时间服务器设备以使用 chrony 守护程序提供时间同步。

我的 c++ 应用程序以 50Hz 的频率读取测量值,并带有相关的时间戳,但是,我想在数据中设置一个标志来报告系统时间是否正确。

通过命令行 timedatectl 可用于报告“NTP 同步”状态。

:~$ timedatectl
      Local time: Wed 2020-08-19 17:03:01 BST
  Universal time: Wed 2020-08-19 16:03:01 UTC
        RTC time: Wed 2020-08-19 16:03:01
       Time zone: Europe/London (BST, +0100)
 Network time on: yes
NTP synchronized: yes
 RTC in local TZ: no

并且 chrony 守护进程的状态将报告系统时钟调整(请注意,大的时间调整是由于出于测试目的设置的一些虚假日期造成的)。

sudo systemctl status chrony
● chrony.service - LSB: Controls chronyd NTP time daemon
   Loaded: loaded (/etc/init.d/chrony; bad; vendor preset: enabled)
   Active: active (running) since Mon 2006-10-02 18:00:28 BST; 13 years 10 months ago
     Docs: man:systemd-sysv-generator(8)
  Process: 3201 ExecStop=/etc/init.d/chrony stop (code=exited, status=0/SUCCESS)
  Process: 3240 ExecStart=/etc/init.d/chrony start (code=exited, status=0/SUCCESS)
    Tasks: 1
   Memory: 340.0K
      CPU: 90ms
   CGroup: /system.slice/chrony.service
           └─3247 /usr/sbin/chronyd

Oct 02 18:00:26 systemd[1]: Starting LSB: Controls chronyd NTP time daemon...
Oct 02 18:00:26 chronyd[3247]: chronyd version 2.1.1 starting (+CMDMON +NTP +REFCLOCK +RTC +PR
Oct 02 18:00:26 chronyd[3247]: Frequency -5.049 +/- 2.705 ppm read from /var/lib/chrony/chrony
Oct 02 18:00:28 chrony[3240]: chronyd is running and online.
Oct 02 18:00:28 systemd[1]: Started LSB: Controls chronyd NTP time daemon.
Oct 02 18:00:30 chronyd[3247]: Selected source 10.10.11.20
Oct 02 18:00:30 chronyd[3247]: System clock wrong by 438114471.141858 seconds, adjustment star
Aug 20 12:28:21 chronyd[3247]: System clock was stepped by 438114471.141858 seconds

当然,这些命令可以通过眼睛观察到,并且可以将报告的时间与预期的时间进行比较,但是我希望我的软件应用程序能够确定报告的时间是否正确。

因此,我想知道如何以编程方式检测当前时间是否已同步,以及理想情况下检测上次同步调整。

编辑:我只是想能够检测当前时间是否在我的 c++ 应用程序中同步。我有一个外部同步源,因此想知道它是否可以运行并提供同步,以便我可以在数据中报告与数据相关的时间戳已同步。我的软件应用程序运行的系统将在没有互联网访问的船上使用。

答案1

4.38 亿秒的偏移量是 13 年。如果此系统有实时时钟,请检查它是否正常工作。

决定在系统启动时是否希望等待 NTP 同步后再启动应用程序。在 RHEL 上,您的单元可以依赖于chrony-wait.service。其实现利用chronyc waitsync

典型的 NTP 指标是可到达对等点的数量以及此系统的偏移量。请参阅Paul Gear 的 ntpmonchronyc用于解析或二进制文件输出的实现ntpq

内核时间纪律是一个频繁而渐进的事情,chrony 会被ntp_adjtime()大量调用。

也许您希望检测像 chrony 记录的这个大步骤?chrony 有一个电子邮件回调,mailonchange指令。它调用sendmail,因此您可以对该邮件执行某些操作,或放置其他脚本。

有多种方法可以从 C 程序中检测这些情况。调用ntp_adjtime()自己并检测返回TIME_ERROR是否存在问题。或者在 Linux 上,使用设置一个长时间运行的计时器timerfd_settime并提供TFD_TIMER_CANCEL_ON_SET标志。如果时钟步进或出现不连续变化,则取消此计时器,这是一个巧妙的技巧。

相关内容