NTP文档翻译:它是如何工作的?How does it work?
此小节说明的是,网络时间协议( NTP )是如何构建并且维护一个正常工作的时间同步网络的。
此处说明一些基本概念,以便帮助理解:计划、配置和维护时间同步协议过程 中 的一些细节。 此小节主要关注理论问题。
参考时钟,指的是一个设备或机器,它会 向外告之当前时间。参考时钟 的关键之处在于精确性:参考时钟必须按照某 种时间标准来精确地反应当前时间。
典型的参考时钟是( 狠贵 )铯钟。便宜 点的(因此也更常见)就是从一些国家标准机构接收广播信号的设备了。 这方面的例子就是一个全球定位系统( GPS (Global Positioning System))接收器,它会从卫 星上接收时间信息。 而那些卫星呢,自身就带有一个铯原子钟,定期校正以保证最大限度 的精确性。
再更便宜(因此更不精确)的参考时钟,使用的就是 地球上的广播信号了,比如 DCF77 、 MSF 和 WWV 。
在网络时间协议中,这些时间参考源被命名为 第0 级 时钟源(stratum 0),意味着它们具有最高的精确性。 (每个 从参考时钟校正 其时间的系统,都可以作为其它系统的时间参考源,但是 ,对于每一 组同步关系,其层级数就加1 。 )
显然,参考时钟会提供当前时间。网络时间 协议会计算一些额外的统计值,以便判断 它所接收到的时间信息的质量。其中 一些值包括:偏移 (offset)( 或叫相位(phase) ) 、抖动 (jitter)(或叫标准差(dispersion))、频率错误(frequency error)和稳定性(stability)(参考 3.3 小节 )。所以 ,每个网络时间协议服务器都会评估 它的参考时钟和它自身的时间质量。
网络时间协议客户端可通过多种方法来获取 要使用的网络时间协议服务器的信息:
可手动配置要用于查询时间信息的服务器 |
服务器可向一个节点直接发送时间信息 |
服务器可使用多播或广播地址来发送时间信息 |
理想情况下,参考时钟 在全世界都是一致的。 一旦同步完成, 在操作系统的时钟与参考时钟之间应当就不会有任何差别了。因此 ,网络时间协议并没有专门处理 这种情况。
不过呢, ntpd 还是会根据自身时钟 与参考时钟之间的偏移量来作出响应的。对于微 小的 (tiny) 偏移量, ntpd 会按照通常做 法来调整本地时钟;对于较小 的(small)和大的(larger)的偏移量, ntpd 会在一段时间之内屏蔽 掉(reject)该参考时钟。对于 后一种情况,操作系统时钟 会以最后一次正常校正的情况为基础继续运行,因为 新的参考时间信息已经被屏蔽了。 过一段时间之后, 小的(small)偏移量( 小于1秒 )会被扭转 (slewed) (缓慢地调整) , 而较大的(larger)偏移量 会导致时钟发生前跳(stepped)(重新设置)。巨大 的(Huge)偏移量会被屏蔽,并且 ntpd 会自行退出,因为它认为已经 发生了某种非常奇怪的事了。
显而易见地, 此算法 也 会在 ntpd 被第一次启动或重启时执行。
运行于 第1级的服务器就是可用 的最好的网络时间协议服务器了,因为 它附着 于一个参考时钟(参考 什么 是参考时钟? )。由于精确 的参考时钟非常昂贵,所以 这种级别的服务器狠少有对公众开放的。
一个第1级服务器, 不仅仅要拥有一个精确 的、精心维护的、精心校准的参考时钟, 还 要具有 高可用性,因为其它系统可能依赖 与它提供的时间服务。也许 那就是并非所有 带参考时钟的 网络时间协议服务器 都对公众开放的原因。
时间可以从一个时间源传送到另一个时间源,一般是 以一个带有参考时钟的第1级服务器作为最初源头的。那些 与第1级服务器同步的服务器会成为第2级服务器。通常 , 一个服务器的层级数会在它所参考的服务器的层级数上加1(参考 Q: 5.1.4.1. )。
将一个客户端与一个网络服务器同步的过程中 要进行几次数据包交互。其中每次交互 都是一次请求/应答过程。 在发出请求时,客户 端将自己的时间( 发送者 时间 戳 )储存在要发送的数据包里。 当服务器收到 这样一个数据包时, 它 又会将自己的时间(接收 者时间戳 )储存到数据包里,并且 在向数据包里储存一个传输时间戳之后就回发数据包。收到回复之后 ,接收 者(客户端) 会再次记录自己的接收时间,以便 估算出数据包 传输 所花费 的时间。假设双向 的延迟是接近的 (symmetrical) ,则传输时间 (延迟)就 被认为 是 “整个延迟减去远程处理时间”的一半。
那些时间差异可用来估算 两台机器之间的时间偏移和标准差(dispersion) (最大偏移错误(maximum offset error)) 。来回时间 越是短、对称,所估算的当前时间就越是准确。
在进行了多次通过了完整性校验的数据 包交互之后,时间才被确信是可靠的。来自 于某台服务器的数据包,只有在满足了协议中定义的那些条件之后,才会认为 是有效的。 时间不会从一个被协议认为是无效的服务器上同步。 对于每个服务器,都出于统计目的收集了一些必要的数据,然后进行多阶段的过滤,以便改进及评估该服务器提供的时间信息的质量。所有用到 的服务器都会被持久地评估。万一各个服务器之间 的数据不一致呢, 就会采用数量最多的那一组服务器( 大流(truechimers) )来产生一个组合的参考时间, 同时将其它服务器声明为无效的( 不准的(falsetickers) )。
通常情况下,要花费大约5分钟( 5个有效的时间样本 )才会使用一个网络时间协议服务器被接受为同步源。 有意思的是,根据协议的定义,对于本地的毫无网络延迟问题 的 参考时钟,也是这样的(也要花这么久)。
经过最初的同步之后,客户 端估算出的质量通常会随着时间而逐渐改善。随着 一个客户端自身变得起来越准确,会有更多的服务器被认为是无效的。
网络时间协议使用 用户数据报(UDP)/网络协议(IP)数据包来进行数据传输,因为这种方式建立连接狠快,响应也狠快。网络时间协议 的官方端口号( ntpd 和 ntpdate 监听 及访问的端口号 )是 123 。
在 news://comp.protocols.time.ntp 中,有一个狠好的答案,来自于 Don Payette ,这里稍微修改了一下:
网络时间协议的时间戳是一个64位的二进制值,并且 在前后两个32位的部分之间暗含着一个小数点。只需如此 ,便可以得到正确的值: 将所有的位 以 一个64位的无符号整数 的形式读取 , 再将它装入一个拥有至少 64位尾数(mantissa)(通常 就是双精度浮点数(double) )的浮点数变量中,然后 以浮点数除法除以 2^32 。
举个例子,以下的64位二进制值:
00000000000000000000000000000001 10000000000000000000000000000000
等价于十进制的1.5。小数 点右边各个位的数值单位(multipliers)分别是1/2、1/4、1/8、1/16 等。
另外,妳应当了解,网络时间协议的时间是从 1900 年开始的,而系统的时间是从 1970 年 开始的。因此 ,以下的值都对应于 2000-08-31_18:52:30.735861
UNIX: 39aea96e.000b3a75
00111001 10101110 10101001 01101110.
00000000 00001011 00111010 01110101
NTP: bd5927ee.bc616000
10111101 01011001 00100111 11101110.
10111100 01100001 01100000 00000000
在向服务器查询的时候,会使用一个与 Q: 5.1.3.3. 中描述的算法类似的算法。基本 要求是,抖动 值 (jitter)( 白噪声(white phase noise) )不应当超过漂移值(wander)(随机 游走频率噪声(random walk frequency noise) )。查询时间间隔尽量保持 在全部噪声值最小的时间点, 这种算法被 称做阿兰插值(Allan intercept), 同时时间间隔总是2的指数。 所允许的最小及最大指数值可使用 minpoll 和 maxpoll 来分别指定(参考 Q: 5.1.5.1. )。对于最近版本 的 ntpd ,如果选中了一个本地的低抖动参考时钟来同步系统时间的话,则对远程的那些服务器的查询会比没有本地参考时钟存在 时 的情况更频繁。 这么做是为了尽可能快地探测到 有错误的参数时钟。 [1]
从 第3小节 中可找到一般性的讨论。另外需要注意 ,修正过程 是渐进式的,所以,可能一共要持续3个小时才会将频率错误完全修正过来(参考 图3 )。
显然,最终能够达到的准确 度是取决于所用的时间源的。显然 ,没有客户端会比它的服务器的时间更准确。另外 ,网络连接的质量也影响到准确性。低速、不稳定的网络会严重影响到时间同步效果。
服务器和客户端之间的时间差必须小于128毫秒,才能维持一个网络时间协议的同步状态。 互联网的典型精确度是在5毫秒到100毫秒的范围内,这是受网络延迟影响的。近期的一项调查 [2] 表明,90%的网络时间协议服务器的网络延迟都低于100毫秒,并且大约99%的服务器都能在1秒之内与同步节点达成同步状态。
由于时间本身是一个连续、稳定的物理流,所以 ntpd 会对时钟进行细微的调整。然而,为了有效地更正时钟错误,这些细微的调整必须频繁进行。如果使用 了 adjtime() ,那么 ntpd 会每秒更新一次系统时钟。如果 ntp_adjtime() 是可用状态的,那么操作系统会自动修正时钟错误,这种情况下仅仅需要极少的主动更新。参考 Section 5.2 和 Q: 5.1.6.1. 。
网络时间协议维护 着一个内部的时钟质量指标。如果时钟 看起来狠稳定,那么修正值会以一个不太频繁的频率来更新。如果时钟 看起来不太稳定,那么就会有更频繁的更新发生了。
有一个决策变量,叫做 poll adjust ,可使用 ntpdc 的 loopinfo 命令来查询。 值为 -30 就表示要降低查询间隔,而值为 30 就表示要增加它(当然是在 minpoll 与 maxpoll 的范围内调整)。 watchdog timer 的值表示的是自动上次更新以来所过的时间。
ntpdc> loopinfo
offset: -0.000102 s
frequency: 16.795 ppm
poll adjust: 6
watchdog timer: 63 s
较近版本的 ntpd (例如 4.1.0 )好象会不太频繁地更新修正值,这可能引起问题。即使参考时间 源被狠频繁地查询,本地的系统时钟也不会被那么频繁地调整。
这个限制实际上取决于狠多因素,比如处理器的速度以及网络带宽,不过这个限制值是非常高的。 Terje Mathisen曾经做过一个计算:
2个数据包/256秒* 500千机器-> 4千数据包/秒(双向各一半)。
数据包尺寸接近于网络上数据包的最小值了,绝对会小于128字节,即使是启用了加密认证也是如此:
4千 * 128 -> 512 KB/s.
所以,只要妳的每台服务器都拥有独立的100 Mbit/s的全双工带宽,那么平均 的网络带宽负载最大也只会是2-3%。
层是对于同步距离的一个度量。 与抖动和延迟不同的是,层是一个更加静态的度量手段。简单 来说(或者 说从客户端的角度来看 ), 它指的 就是与参考时钟之间的服务器数量。所以 ,参考时钟本身是第0层,而最接近的服务器就是第1层。 在网络上,不会有发自第0层的网络时间协议数据包。
一个服务器,如果它是与第 n 层的服务器同步的,那么它自身是运行于第 n + 1 层的。层数的上限是 15 。引入 层这个概念的目的是,通过优先使用较低层数的服务器来避免同步过程陷入循环。
在同步循环的情况下,从某个特定的由一些服务器组成的路径上得到的来自于某个时间源的时间,会又在这样一个路径上再次被用作参考时间。 这可能会引起错误的过度累积,因而是需要避免的。所以网络时间协议采用多种手段相结合,以解决这个问题:
•.时间源的网络地址会被用作参考标识,以避免重复。然而参考标识被限制为32位。
•. Q: 5.1.4.1. 中描述的层概念被用来形成一个无环的同步网络。
更准确地说 [2] , 此算法会以跳数为 同步距离的 主要度量值来找到一个最短路径生成树。参考标识 是一种辅助手段,用于在网络拓扑频繁变化的情况下避免相邻节点之间的环。 这是此类算法的一个已知问题。参考任何 一本关于网络路由算法的教科书,以了解更多细节。顺便推荐一下Bertsekas 和Gallagher 写的 计算机网络 。
在IPv6 中,参考标识字段 是一个时间戳,可用于同样的目的。
对于网络时间协议,重新启动之后,默认的查询间隔值由 minpoll 指定。 minpoll 和 maxpoll 的默认值分别是 6 ( 64秒 )和 10 ( 1024秒 )。
对于xntp3-5.93e,允许 的 最小 和最大查询间隔值分别是 4 ( 16秒 )和 14 ( 4.5小时 )。
对于ntp-4.0.99f,允许的最小和最大查询间隔值分别是 4 ( 16秒 )和 17 ( 1.5天 )。 这些值是在文件 ntp.h 中指定的。
实际上并不存在固定答案: 查询时间间隔较短呢,就会频繁地更新各个参数,同时也对抖动和随机错误更敏感。查询时间间隔 较长呢,那么当两次更新之间发生了明显的错误时,就需要做更大动作的修正了。然而,目前看来 有一个比较理想的值。对于普通 的操作系统时钟来说, 这个最佳值正好是默认的最大查询时间间隔,1024秒。参考 Q: 5.1.3.1. 。
为了维护一个正确的时钟, xntpd 就必须对系统时钟作出调整。 不同的操作系统提供了不同的手段, 以下列出的是最常见的手段。
简单来说, 一个具体的网络时间协议软件可使用4种机制(系统调用)来调整系统时钟 ( 要想了解更多,就去看 表格4 中的那些标准( RFC s ) ):
•. settimeofday(2) 用于大幅调整(step)(设置)时间。当时间的偏差超过128毫秒时会使用这个方法。
•. adjtime(2) 用于小幅调整(slew)(逐渐改变)时间。小幅调整时间 ,意思就是改变软件时钟的虚拟频率,以让时钟走得快一点或慢一点,直到达到了所需要的修正值。 要想利用小幅调整手段来改变一大段时间的话,这个过程也要花费较长时间。比如 说,标准的Linux 内核,其调整速度是0.5毫秒每秒。
•. ntp_adjtime(2)用于调整软件时钟 的多个参数( 也被称作内核调整(kernel discipline) )。包括 以下参数:
•.调整软件时钟的偏移量,可能会同时调整虚拟频率
•.直接调整软件时钟的虚拟频率
•.启用或禁用 PPS事件处理
•.控制对于闰秒的处理过程
•.读取及定稿时钟的某些相关字符值
•. hardpps() 是一个函数,只会被操作系统内部的中断服务程序调用。如果启用 了,那么 hardpps() 就会根据 一个外部信号来更新内核时钟的频率和偏移量(参考 6.2.4 小节 )。
这个声明是来自于 Professor David L. Mills 的一封邮件。当时 是针对版本 4.1.0 中的一个漏洞作出回应。 |
|
...Professor David L. Mills 说的... |
这个衣裳好看
HxLauncher: Launch Android applications by voice commands