Ответы:
Время прохождения туда и обратно нигде не хранится. Хост-отправитель запоминает время отправки каждого сообщения эхо-запроса ICMP, используя 16-битные поля идентификатора и последовательности ICMP. Когда он получает эхо-ответ ICMP, он отмечает текущее время, находит время, когда он отправил соответствующий пакет запроса, идентифицированный ответом, вычисляет разницу и сообщает о ней.
Обычно ping использует поле идентификации ICMP, чтобы различать несколько одновременных пингов, и поле последовательности, чтобы различать отдельные пакеты.
Реализация решает, где хранить исходящее время для данного пакета: вместо того, чтобы хранить его на хосте в таблице, он обычно отправляет его в исходящем запросе и использует копию в ответе для вычисления времени. (Спасибо комментаторам за указание на это.) Он отправляется любым удобным для реализации способом и, конечно, должен доверять удаленному концу и любому промежуточному оборудованию, чтобы правильно копировать данные. Известно, что некоторые системы представляют время в 16 байтах с разрешением в микросекундах, а некоторые - в 8 байтов с разрешением в миллисекундах.
Формат внутри data
части IP-пакета - это сообщение эхо-запроса ICMP / ответа, скопированное сюда из RFC 792 «Формат сообщения управления Интернетом» (p14).
Type
8 для запроса, 0 для ответа; Code
это 0.
0 1 2 3
0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Type | Code | Checksum |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Identifier | Sequence Number |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Data ...
+-+-+-+-+-
PS. Для ясности, поле идентификации заголовка IP обычно устанавливается на произвольное значение, отличающееся для каждого исходящего пакета, используется для повторной сборки любой фрагментации и не имеет того же значения, что и что-либо в теле ICMP.
Кроме того, хотя существует механизм, определенный для помещения меток времени в заголовок IP в качестве опции, это не является обычным механизмом для проверки связи, поскольку очень многие маршрутизаторы настроены так, чтобы не пропускать определенные параметры IP. См. RFC 781 Спецификация опции метки времени интернет-протокола.
Наконец, хотя все здесь было написано с точки зрения IPv4, согласно первоначальному вопросу; но ping в IPv6 чрезвычайно похож, см. ICMPv6 RFC 4443 .
ping
Linux есть хотя бы одна реализация, которая хранит метку времени в Data
разделе полезной нагрузки ICMP. Это привело к довольно интересному сообщению об ошибке, когда эхо-ответы проходили через интернет-обмен, который немного портился в этом месте в каждом пакете.
По крайней мере, с помощью обычной ping
утилиты в Linux время отправки пакета сохраняется в части данных пакета эхо-запроса, то есть после заголовков IP и ICMP. Часть данных остается неизменной, когда получатель отвечает эхо-ответом, поэтому отправитель может рассчитать время прохождения туда-обратно.
Это описано на странице man для ping
утилиты (в разделе «ПОДРОБНЫЕ ПАКЕТЫ ICMP»):
Если пространство данных имеет размер
struct timeval
пинга, по крайней мере, использует начальные байты этого пространства, чтобы включить временную метку, которую он использует при вычислении времени прохождения туда-обратно. Если пространство данных короче, время прохождения туда и обратно не указывается.
На моей машине sizeof(struct timeval)
16, поэтому установка размера пакетных данных на 15 не дает возможности ping
показывать время прохождения туда-обратно:
$ ping -s 15 8.8.8.8
PING 8.8.8.8 (8.8.8.8) 15(43) bytes of data.
23 bytes from 8.8.8.8: icmp_seq=1 ttl=121
Конечно, сохранение метки времени отправки в утилите, как описывает ответ @ jonathanjo, также будет возможной реализацией. Даже утилита Linux нуждается во внутренней бухгалтерии, так как она обнаруживает дубликаты пакетов.