Я понимаю, как работают аки и окна. Я не понимаю, почему я наблюдаю следующее поведение при захвате пакетов
Client Server
data1----->
data2----->
<--------ack
Когда сервер запрашивает data2, как клиент узнает, что data1 не был потерян? Поскольку я не вижу ACK для этих данных.
Короче говоря, один ACK подтвердил оба пакета, которые вы просматриваете.
Для каждых данных не обязательно должен быть специальный пакет ACK.
Хотя в TCP есть усовершенствование, называемое выборочным подтверждением, TCP не требует его строго. (Но опять же, это есть в большинстве стеков в наши дни)
Обычные ACK являются частью заголовка TCP. если в поле флагов установлен флаг ACK, то номер подтверждения означает, что данные до этого момента были проверены. Этот флаг обычно устанавливается для каждого пакета, кроме первого. В другом поле указано, что в нем есть место для приема определенного количества дополнительных данных.
Или классическое искусство ASCII из RFC 793
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
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Source Port | Destination Port |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Sequence Number |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Acknowledgment Number |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Data | |U|A|P|R|S|F| |
| Offset| Reserved |R|C|S|S|Y|I| Window |
| | |G|K|H|T|N|N| |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Checksum | Urgent Pointer |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Options | Padding |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| data |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
Как вы говорите «сегменты», я предполагаю, что это TCP.
Следовательно, ACK не подтверждает пакеты, он признает данные. Как сказано в @infixed, «если в поле флагов установлен флаг ACK, то номер подтверждения говорит о том, что данные до этой точки были проверены» - если первый клиентский сегмент TCP отправил данные с (относительными) порядковыми номерами от 0 до 24 - т. е. 25 байтов данных, начиная с (относительного) порядкового номера 0 - и второй клиентский сегмент TCP отправил данные с (относительными) порядковыми номерами 25-49, то есть 25 байтов данных, начиная с (относительного) порядкового номера 25, который является (относительным) порядковым номером для первого байта после первого сегмента - тогда сервер может отправить пакет с сообщением «Я получил все данные до (относительного) порядкового номера 49», который подтверждает данные из обе этих пакетов.
Кроме того, как сказал @infixed, есть опция TCP, которая позволяет получателю подтверждать некоторые, но не все данные в заданном диапазоне. Если первый сегмент TCP не дошел до сервера, а второй - сделал это, сервер мог бы использовать «выборочное подтверждение», чтобы сказать: «Я получил все данные между (относительными) порядковыми номерами 25 и 49», чтобы клиент будет знать, что ему придется повторно передать первый сегмент, но не второй сегмент.