使用 systemd 控制计算机时间和日期

使用 NTP、Chrony 和 systemd-timesyncd 使您的计算机时间保持同步。
115 位读者喜欢这篇文章。
Clocks

Matteo Ianeselli。由 Opensource.com 修改。 CC-BY-3.0。

大多数人都关心时间。我们及时起床进行早晨的例行事务并通勤上班(对于我们许多人来说,这些天都是短途旅行),休息一下吃午饭,赶上项目截止日期,庆祝生日和节假日,赶飞机等等。

我们中的一些人甚至痴迷于时间。我的手表是太阳能的,并通过位于科罗拉多州柯林斯堡的国家标准与技术研究院 (NIST) ,通过位于那里的WWVB 时间信号无线电台获取精确时间。时间信号与原子钟同步,原子钟也位于柯林斯堡。我的 Fitbit 与我的手机同步,我的手机与 网络时间协议 (NTP) 服务器同步,该服务器最终与原子钟同步。

为什么时间对计算机很重要

我们的设备和计算机需要精确的时间有很多原因。例如,在银行业、股票市场和其他金融业务中,交易必须按正确的顺序维护,而精确的时间顺序对此至关重要。

我们的手机、平板电脑、汽车、GPS 系统和计算机都需要精确的时间和日期设置。我希望我的计算机桌面上的时钟是正确的,这样我就可以依靠本地日历应用程序在正确的时间弹出提醒。正确的时间还可以确保 SystemV cron 作业和 systemd 定时器在正确的时间触发。

正确的时间对于日志记录也很重要,因此根据时间更容易找到特定的日志条目。举个例子,我曾经在北卡罗来纳州电子邮件系统的 DevOps 部门工作(当时不叫这个名字)。我们过去每天处理超过 2000 万封电子邮件。当相关计算机保持精确时间时,通过一系列服务器跟踪电子邮件或通过使用地理上分散的主机上的日志文件确定确切的事件顺序会容易得多。

多个时间

Linux 主机有两个时间需要考虑:系统时间和 RTC 时间。RTC 代表实时时钟,这是一个花哨但不太准确的系统硬件时钟名称。

即使计算机关闭,硬件时钟也会通过系统主板上的电池持续运行。RTC 的主要功能是在无法连接到时间服务器时保持时间。在个人电脑的黑暗时代,没有互联网连接到时间服务器,因此计算机可用的唯一时间是内部时钟。操作系统必须在启动时依赖 RTC,用户必须使用硬件 BIOS 配置界面手动设置系统时间,以确保其正确。

硬件时钟不理解时区的概念;只有时间存储在 RTC 中,而不是时区或与 UTC(协调世界时,也称为 GMT 或格林威治标准时间)的偏移量。您可以使用我将在本文后面探讨的工具设置 RTC。

系统时间是操作系统已知的时间。它是您在桌面的 GUI 时钟上、date 命令的输出中、日志的时间戳以及文件访问、修改和更改时间中看到的时间。

rtc 手册页包含关于 RTC 和系统时钟以及 RTC 功能的更完整的讨论。

NTP 怎么样?

世界各地的计算机都使用 NTP(网络时间协议)通过 NTP 服务器的层次结构将其时间与互联网标准参考时钟同步。主时间服务器位于 stratum 1 层,它们通过卫星、无线电甚至电话线上的调制解调器直接连接到 stratum 0 层的各种国家时间服务。stratum 0 层的时间服务可以是原子钟、无线电接收器(调谐到原子钟广播的信号)或使用 GPS 卫星广播的高度精确的时钟信号的 GPS 接收器。

为了防止来自层次结构中较低(即 stratum 编号较高)的时间服务器或客户端的时间请求压垮主参考服务器,数千个公共 NTP stratum 2 服务器开放并可供所有人使用。许多组织和用户(包括我)拥有大量需要 NTP 服务器的主机,他们选择设置自己的时间服务器,因此只有一个本地主机访问 stratum 2 或 3 时间服务器。然后,他们配置网络中的其余主机以使用本地时间服务器。就我的家庭网络而言,那是一个 stratum 3 服务器。

NTP 实现选项

最初的 NTP 实现是 ntpd,后来又加入了两个更新的实现,chronydsystemd-timesyncd。这三者都使本地主机的时间与 NTP 时间服务器同步。systemd-timesyncd 服务不如 chronyd 强大,但对于大多数用途来说已经足够了。如果 RTC 严重不同步,它可以执行大的时间跳跃,并且如果本地系统时间稍微漂移,它可以逐渐调整系统时间以与 NTP 服务器保持同步。systemd-timesync 服务不能用作时间服务器。

Chrony 是一个 NTP 实现,包含两个程序:chronyd 守护程序和一个名为 chronyc 的命令行界面。正如我在之前的文章中解释的那样,Chrony 具有一些使其成为许多环境的最佳选择的功能,主要是

  • Chrony 可以比旧的 ntpd 服务更快地与时间服务器同步。这对于不经常运行的笔记本电脑或台式机很有用。
  • 它可以补偿时钟频率的波动,例如当主机休眠或进入睡眠模式时,或者当时钟速度由于频率步进而变化,从而在负载较低时减慢时钟速度。
  • 它可以处理间歇性网络连接和带宽饱和。
  • 它可以调整网络延迟和延迟。
  • 在初始时间同步之后,Chrony 永远不会停止时钟。这确保了许多系统服务和应用程序的稳定和一致的时间间隔。
  • 即使没有网络连接,Chrony 也可以工作。在这种情况下,可以手动更新本地主机或服务器。
  • Chrony 可以充当 NTP 服务器。

需要明确的是,NTP 是一种协议,它使用 Chrony 或 systemd-timesyncd.service 在 Linux 主机上实现。

NTP、Chrony 和 systemd-timesyncd RPM 软件包在标准的 Fedora 存储库中可用。systemd-udev RPM 是一个基于规则的设备节点和内核事件管理器,Fedora 默认安装了它,但未启用。

您可以安装所有这三个并在这三者之间切换,但这很麻烦,不值得这样做。最新版本的 Fedora、CentOS 和 RHEL 已从 NTP 转向 Chrony 作为其默认的时间保持实现,并且它们也安装了 systemd-timesyncd。我发现 Chrony 运行良好,提供了比 NTP 服务更好的界面,提供了更多的信息,并增加了控制,这些都是系统管理员的优势。

禁用其他 NTP 服务

您的主机上可能已经运行了 NTP 服务。如果是这样,您需要在切换到其他服务之前禁用它。我一直在使用 chronyd,所以我使用以下命令停止并禁用它。为您在主机上使用的任何 NTP 守护程序运行适当的命令

[root@testvm1 ~]# systemctl disable chronyd ; systemctl stop chronyd
Removed /etc/systemd/system/multi-user.target.wants/chronyd.service.
[root@testvm1 ~]#

验证它是否已停止和禁用

[root@testvm1 ~]# systemctl status chronyd
● chronyd.service - NTP client/server
     Loaded: loaded (/usr/lib/systemd/system/chronyd.service; disabled; vendor preset: enabled)
     Active: inactive (dead)
       Docs: man:chronyd(8)
             man:chrony.conf(5)
[root@testvm1 ~]#

启动前检查状态

systemd timesync 的状态指示 systemd 是否已启动 NTP 服务。因为您尚未启动 systemd NTP,所以 timesync-status 命令不返回任何数据

[root@testvm1 ~]# timedatectl timesync-status 
Failed to query server: Could not activate remote peer.

但是直接的 status 请求提供了一些重要信息。例如,不带参数或选项的 timedatectl 命令隐含默认的 status 子命令

[root@testvm1 ~]# timedatectl status
           Local time: Fri 2020-05-15 08:43:10 EDT  
           Universal time: Fri 2020-05-15 12:43:10 UTC  
                 RTC time: Fri 2020-05-15 08:43:08      
                Time zone: America/New_York (EDT, -0400)
System clock synchronized: no                           
              NTP service: inactive                     
          RTC in local TZ: yes                    

Warning: The system is configured to read the RTC time in the local time zone.
         This mode cannot be fully supported. It will create various problems
         with time zone changes and daylight saving time adjustments. The RTC
         time is never updated, it relies on external facilities to maintain it.
         If at all possible, use RTC in UTC by calling
         'timedatectl set-local-rtc 0'.
[root@testvm1 ~]#

这会返回您主机的本地时间、UTC 时间和 RTC 时间。它显示系统时间设置为 America/New_York 时区 (TZ),RTC 设置为本地时区的时间,并且 NTP 服务未激活。RTC 时间已开始与系统时间略有偏差。这对于时钟未同步的系统来说是正常的。主机上的漂移量取决于自系统上次同步以来经过的时间以及单位时间的漂移速度。

还有一个关于对 RTC 使用本地时间的警告消息——这与时区更改和夏令时调整有关。如果计算机在需要进行更改时关闭,则 RTC 时间将不会更改。这在 24/7 通电的服务器或其他主机中不是问题。此外,任何提供 NTP 时间同步的服务都将确保主机在启动过程的早期设置为正确的时间,因此它将在完全启动并运行之前是正确的。

设置时区

通常,您在安装过程中设置计算机的时区,并且永远不需要更改它。但是,有时需要更改时区,并且有一些工具可以提供帮助。Linux 使用时区文件来定义主机正在使用的本地时区。这些二进制文件位于 /usr/share/zoneinfo 目录中。我的时区的默认值由链接 /etc/localtime -> ../usr/share/zoneinfo/America/New_York 定义。但是您不需要知道这些来更改时区。

但是您确实需要知道您所在位置的官方时区名称。假设您要将时区更改为洛杉矶

[root@testvm2 ~]# timedatectl list-timezones | column 
<SNIP>
America/La_Paz                  Europe/Budapest
America/Lima                    Europe/Chisinau
America/Los_Angeles             Europe/Copenhagen
America/Maceio                  Europe/Dublin
America/Managua                 Europe/Gibraltar
America/Manaus                  Europe/Helsinki
<SNIP>

现在您可以设置时区了。我使用 date 命令来验证更改,但您也可以使用 timedatectl

[root@testvm2 ~]# date
Tue 19 May 2020 04:47:49 PM EDT
[root@testvm2 ~]# timedatectl set-timezone America/Los_Angeles
[root@testvm2 ~]# date
Tue 19 May 2020 01:48:23 PM PDT
[root@testvm2 ~]#

您现在可以将主机时区更改回本地时区。

systemd-timesyncd

systemd timesync 守护程序提供了一个 NTP 实现,它在 systemd 上下文中易于管理。它默认安装在 Fedora 和 Ubuntu 中,并在 Ubuntu 中默认启动,但在 Fedora 中未启动。我不确定其他发行版;您可以使用以下命令检查您的发行版

[root@testvm1 ~]# systemctl status systemd-timesyncd

配置 systemd-timesyncd

systemd-timesyncd 的配置文件是 /etc/systemd/timesyncd.conf。它是一个简单的文件,包含的选项比旧的 NTP 服务和 chronyd 少。以下是我的 Fedora VM 上此文件的默认版本的完整内容

#  This file is part of systemd.
#
#  systemd is free software; you can redistribute it and/or modify it
#  under the terms of the GNU Lesser General Public License as published by
#  the Free Software Foundation; either version 2.1 of the License, or
#  (at your option) any later version.
#
# Entries in this file show the compile time defaults.
# You can change settings by editing this file.
# Defaults can be restored by simply deleting this file.
#
# See timesyncd.conf(5) for details.

[Time]
#NTP=
#FallbackNTP=0.fedora.pool.ntp.org 1.fedora.pool.ntp.org 2.fedora.pool.ntp.org 3.fedora.pool.ntp.org
#RootDistanceMaxSec=5
#PollIntervalMinSec=32
#PollIntervalMaxSec=2048

除了注释之外,它唯一包含的部分是 [Time],所有行都被注释掉了。这些是默认值,不需要更改或取消注释(除非您有理由这样做)。如果您在 NTP= 行中没有定义特定的 NTP 时间服务器,Fedora 的默认设置是回退到 Fedora 的时间服务器池。我喜欢将我网络上的时间服务器添加到此行

NTP=myntpserver

启动 timesync

启动和启用 systemd-timesyncd 就像任何其他服务一样

[root@testvm2 ~]# systemctl enable systemd-timesyncd.service
Created symlink /etc/systemd/system/dbus-org.freedesktop.timesync1.service → /usr/lib/systemd/system/systemd-timesyncd.service.
Created symlink /etc/systemd/system/sysinit.target.wants/systemd-timesyncd.service → /usr/lib/systemd/system/systemd-timesyncd.service.
[root@testvm2 ~]# systemctl start systemd-timesyncd.service
[root@testvm2 ~]#

设置硬件时钟

这是我的一个系统在启动 timesyncd 后看起来的样子

[root@testvm2 systemd]# timedatectl 
               Local time: Sat 2020-05-16 14:34:54 EDT  
           Universal time: Sat 2020-05-16 18:34:54 UTC  
                 RTC time: Sat 2020-05-16 14:34:53      
                Time zone: America/New_York (EDT, -0400)
System clock synchronized: yes                          
              NTP service: active                       
          RTC in local TZ: no    

RTC 时间与本地时间 (EDT) 相差大约一秒,并且在接下来的几天内差异会增加几秒。由于 RTC 没有时区概念,因此 timedatectl 命令必须进行比较以确定哪个时区匹配。如果 RTC 时间与本地时间不完全匹配,则不认为它位于本地时区。

为了寻找更多信息,我检查了 systemd-timesync.service 的状态,发现

[root@testvm2 systemd]# systemctl status systemd-timesyncd.service 
● systemd-timesyncd.service - Network Time Synchronization
     Loaded: loaded (/usr/lib/systemd/system/systemd-timesyncd.service; enabled; vendor preset: disabled)
     Active: active (running) since Sat 2020-05-16 13:56:53 EDT; 18h ago
       Docs: man:systemd-timesyncd.service(8)
   Main PID: 822 (systemd-timesyn)
     Status: "Initial synchronization to time server 163.237.218.19:123 (2.fedora.pool.ntp.org)."
      Tasks: 2 (limit: 10365)
     Memory: 2.8M
        CPU: 476ms
     CGroup: /system.slice/systemd-timesyncd.service
             └─822 /usr/lib/systemd/systemd-timesyncd

May 16 09:57:24 testvm2.both.org systemd[1]: Starting Network Time Synchronization...
May 16 09:57:24 testvm2.both.org systemd-timesyncd[822]: System clock time unset or jumped backwards, restoring from recorded timestamp: Sat 2020-05-16 13:56:53 EDT
May 16 13:56:53 testvm2.both.org systemd[1]: Started Network Time Synchronization.
May 16 13:57:56 testvm2.both.org systemd-timesyncd[822]: Initial synchronization to time server 163.237.218.19:123 (2.fedora.pool.ntp.org).
[root@testvm2 systemd]#

请注意日志消息,该消息表明系统时钟时间未设置或向后跳跃。timesync 服务从时间戳设置系统时间。时间戳由 timesync 守护程序维护,并在每次成功的时间同步时创建。

timedatectl 命令无法从系统时钟设置硬件时钟的值;它只能从在命令行中输入的值设置时间和日期。但是,您可以使用 hwclock 命令将 RTC 设置为与系统时间相同的值

[root@testvm2 ~]# /sbin/hwclock --systohc --localtime 
[root@testvm2 ~]# timedatectl 
               Local time: Mon 2020-05-18 13:56:46 EDT  
           Universal time: Mon 2020-05-18 17:56:46 UTC  
                 RTC time: Mon 2020-05-18 13:56:46      
                Time zone: America/New_York (EDT, -0400)
System clock synchronized: yes                          
              NTP service: active                       
          RTC in local TZ: yes

--localtime 选项确保硬件时钟设置为本地时间,而不是 UTC。

您真的需要 RTC 吗?

任何 NTP 实现都会在启动序列期间设置系统时钟,那么 RTC 是否必要?并非如此,只要您有到时间服务器的网络连接即可。但是,许多系统无法始终访问网络连接,因此硬件时钟很有用,这样 Linux 就可以读取它并设置系统时间。即使它可能会偏离实际时间,但这仍然比手动设置时间要好。

总结

本文探讨了使用一些 systemd 工具来管理日期、时间和时区。systemd-timesyncd 工具提供了一个不错的 NTP 客户端,它可以使本地主机上的时间与 NTP 服务器同步。但是,systemd-timesyncd 不提供服务器服务,因此,如果您的网络需要 NTP 服务器,则必须使用其他工具,例如 Chrony,充当服务器。

我更喜欢在我的网络中为任何服务使用单一实现,所以我使用 Chrony。如果您不需要本地 NTP 服务器,或者如果您不介意为服务器处理 Chrony,为客户端处理 systemd-timesyncd,并且您不需要 Chrony 的其他功能,那么 systemd-timesyncd 是 NTP 客户端的可行选择。

我想提出的另一点是:您不必使用 systemd 工具来实现 NTP。您可以使用旧的 ntpd 或 Chrony 或其他一些 NTP 实现。systemd 由大量服务组成;其中许多是可选的,因此可以禁用它们并在其位置使用其他服务。它不是有些人认为的庞大、单片的怪物。不喜欢 systemd 或其某些部分是可以的,但您应该做出明智的决定。

我不反感 systemd 的 NTP 实现,但我更喜欢 Chrony,因为它更符合我的需求。这就是 Linux 的全部意义所在。

资源

互联网上有大量关于 systemd 的信息,但其中很多信息都很简洁、晦涩甚至具有误导性。除了本文中提到的资源外,以下网页还提供了关于 systemd 启动的更详细和可靠的信息。

  • Fedora 项目有一个很好的、实用的 systemd 指南。它几乎包含了您需要了解的所有内容,以便使用 systemd 配置、管理和维护 Fedora 计算机。
  • Fedora 项目还有一个很好的 速查表,它将旧的 SystemV 命令交叉引用到可比较的 systemd 命令。
  • 有关 systemd 的详细技术信息以及创建它的原因,请查看 Freedesktop.orgsystemd 描述
  • Linux.com 的 “更多 systemd 乐趣” 提供了更高级的 systemd 信息和技巧

Lennart Poettering,systemd 的设计者和主要开发者,还为 Linux 系统管理员撰写了一系列深入的技术文章。这些文章写于 2010 年 4 月至 2011 年 9 月之间,但它们现在和当时一样具有现实意义。关于 systemd 及其生态系统的大部分其他优秀著作都基于这些论文。

接下来阅读什么

学习喜爱 systemd

systemd 是所有进程之母,负责将 Linux 主机启动到可以进行高效工作的状态。

(通讯员)
2020 年 4 月 16 日
David Both
David Both 是一位开源软件和 GNU/Linux 倡导者、培训师、作家和演讲者。自 1996 年以来,他一直从事 Linux 和开源软件工作,自 1969 年以来一直从事计算机工作。他是“系统管理员 Linux 哲学”的坚定支持者和传播者。

评论已关闭。

Creative Commons License本作品根据 Creative Commons Attribution-Share Alike 4.0 International License 获得许可。
© . All rights reserved.