硬件时间戳(hardstamps)如何工作

网络工程 硬件
2021-07-28 16:03:51

我目前正在深入研究 PTP (IEEE 1588) 和用于捕获网络流量的精确时间戳等主题。Internet 上的许多资源都将硬标记称为网卡的一项功能,允许它们在将数据包放入(通常是非确定性的)应用层队列之前向数据包添加时间戳。

这些时间戳是什么样的?它们是相对于操作系统发送的开始信号还是绝对时间戳来测量的?绝对标记是否与操作系统时钟或由 NIC 管理的时钟同步?

1个回答

时间戳基于 NIC 中的时钟在硬件中发生。根据您的 NIC,有一个 NIC 寄存器,您的时间戳将被写入其中,或者某些卡(Intel 82580)可以将信息添加到数据包缓冲区中。对于将时间戳写入寄存器的卡,您必须先读取寄存器才能为下一个数据包添加时间戳,这有效地限制了您的吞吐量,而 82580 可以为所有数据包添加时间戳。

在 Linux 中,您将在数据包本身之外的数据结构中接收时间戳。这是内核文档中的一些内容:

These timestamps are returned in a control message with cmsg_level
SOL_SOCKET, cmsg_type SCM_TIMESTAMPING, and payload of type

struct scm_timestamping {
    struct timespec ts[3];
};

The structure can return up to three timestamps. This is a legacy
feature. Only one field is non-zero at any time. Most timestamps
are passed in ts[0]. Hardware timestamps are passed in ts[2].

ts[1] used to hold hardware timestamps converted to system time.
Instead, expose the hardware clock device on the NIC directly as
a HW PTP clock source, to allow time conversion in userspace and
optionally synchronize system time with a userspace PTP stack such
as linuxptp. For the PTP clock API, see Documentation/ptp/ptp.txt.

时间戳基于 NIC 时间。我相信您可以修改网卡时钟,但更常见的方法是让网卡时钟自由运行(保证单调时间)并在用户空间中进行任何调整。调整可能包括计算系统时间的偏移量并将所有接收到的时间戳调整为系统时间。内核可以/可以(自从我检查以来已经很长时间了)为您执行此操作,但我相信推荐的方法是在您的用户空间中自己执行此操作。在其他应用程序中,您根本不关心绝对时间,因为数据包之间的相对时间是唯一重要的因素。

我的两个同事基于此编写了一个 SLA 测量应用程序。您可以在GitHub 上找到源代码

还有MoonGen,它是一个基于 DPDK 的框架,具有用于数据包处理的 Lua 脚本能力。他们有一篇出色的论文,其中包括有关时间戳的信息。