Литмир - Электронная Библиотека

С другой стороны, для многих TCP-соединений произведение пропускной способности и времени задержки составляет гораздо больше, чем один сегмент. Рассмотрим соединение, которое передает данные по всей территории США со скоростью 1 Мбит/с, а время, за которое пакет доходит до получателя и обратно, составляет 100 мс. Даже при таком медленном соединении 200 Кбит информации будут храниться на получателе в течение того времени, которое требуется для отправки сегмента и получения подтверждения. В таких случаях следует использовать скользящее окно большого размера. Протокол с остановкой и ожиданием подтверждения серьезно повредит производительности. В нашем примере он ограничил бы передачу одним сегментом в 200 мс (или 5 сегментами в секунду) независимо от реальной скорости сети.

Поскольку транспортные протоколы обычно используют скользящие окна большего размера, мы обсудим процесс буферизации более подробно. Так как у хоста может быть несколько соединений, каждое из которых обрабатывается отдельно, для скользящих окон ему может потребоваться большое количество буферного пространства. Буферы должны использоваться как отправителем, так и получателем. Отправителю буфер нужен для хранения всех переданных сегментов, для которых еще не пришло подтверждение о прибытии, на случай если эти сегменты будут потеряны и их придется отправить повторно.

Зная, что отправитель выполняет буферизацию, получатель может использовать свои буферы по своему усмотрению. Например, получатель может содержать единый буферный накопитель, используемый всеми соединениями. Когда приходит сегмент, предпринимается попытка динамически выделить ему новый буфер. Если это удается, то сегмент принимается, в противном случае он отвергается. Поскольку отправитель готов к тому, чтобы передавать потерянные сегменты повторно, игнорирование сегментов получателем не наносит существенного вреда, хотя и расходует некоторые ресурсы. Отправитель просто повторяет попытки до тех пор, пока не получит подтверждения.

Выбор компромиссного решения между буферированием у отправителя и у получателя зависит от типа трафика соединения. Если трафик импульсный, небольшой мощности, как, например, трафик интерактивного терминала, лучше не выделять никаких буферов, а получать их динамически на обоих концах, полагаясь на буферизацию со стороны отправителя (на случай, если сегменты будут случайно удалены). С другой стороны, при передаче файла будет лучше, если получатель выделит целое окно буферов, чтобы данные могли передаваться с максимальной скоростью. Такую стратегию использует TCP.

Тем не менее открытым остается вопрос об организации набора буферов. Если большинство сегментов имеют примерно одинаковые размеры, естественно организовать буферы в виде массива буферов равной величины, каждый из которых может вместить один сегмент, как показано на рис. 6.12, а. Однако если сегменты сильно отличаются по размеру, от коротких запросов на загрузку веб-страниц до крупных пакетов при одноранговой передаче файлов, массив из буферов фиксированного размера окажется неудобным. Если размер буфера выбирать равным наибольшему возможному сегменту, то при хранении небольших сегментов память будет расходоваться неэффективно. Если же сделать размер буфера меньшим, тогда для хранения большого сегмента потребуется несколько буферов с сопутствующими сложностями.

Компьютерные сети. 5-е издание - _331.jpg

Рис. 6.12. Организация набора буферов: а — цепочка буферов фиксированного размера; б — цепочка буферов переменного размера; в — один большой циклический буфер

для одного соединения

Другой метод решения указанной проблемы состоит в использовании буферов переменного размера, как показано на рис. 6.12, б. Преимущество этого метода заключается в более оптимальном использовании памяти, но платой за это является усложненное управление буферами. Третий вариант состоит в выделении соединению единого большого циклического буфера, как показано на рис. 6.12, в. Эта простая и изящная схема работает независимо от размера сегментов, однако она хорошо использует память, только если все соединения сильно нагружены.

При открытии и закрытии соединений и при изменении формы трафика отправитель и получатель должны динамически изменять выделенные буферы. Следовательно, транспортный протокол должен позволять отправителю посылать запросы на выделение буфера на другом конце. Буферы могут выделяться для каждого соединения или коллективно на все соединения между двумя хостами. В качестве альтернативы запросам буферов, получатель, зная состояние своих буферов, но не зная, какой трафик ему будет предложен, может сообщить отправителю, что он зарезервировал для него Х буферов. При увеличении числа открытых соединений может потребоваться уменьшить количество или размеры выделенных буферов. Протокол должен предоставлять такую возможность.

В отличие от протоколов скользящего окна, описанных в главе 3, для реализации динамического выделения буферов следует отделить буферизацию от подтверждений. Динамическое выделение буферов означает, на самом деле, использование окна переменного размера. Вначале отправитель, основываясь на своих потребностях, запрашивает определенное количество буферов. Получатель выделяет столько, сколько может. При отправлении каждого сегмента отправитель должен уменьшать на единицу число буферов, а когда это число достигнет нуля, он должен остановиться. Получатель отправляет обратно на попутных сегментах отдельно подтверждения и информацию об имеющихся у него свободных буферах. Эта схема используется в TCP; при этом информация о буферах хранится в поле заголовка Window size.

На рис. 6.13 показан пример управления динамическим окном в дейтаграммной сети с 4-битными порядковыми номерами. В этом примере данные передаются в виде сегментов от хоста A к хосту B, а подтверждения и запросы на предоставление буферов идут в обратном направлении (также в виде сегментов). Вначале хост A запрашивает 8 буферов, но ему выделяется только 4. Затем он посылает три сегмента, из которых последний теряется. На шаге 6 хост A получает подтверждение получения посланных им сегментов 0 и 1, в результате чего хост А может освободить буферы и послать еще три сегмента (с порядковыми номерами 2, 3 и 4). Хост A знает, что сегмент номер 2 он уже посылал, поэтому он думает, что может послать сегменты 3 и 4, что он и делает. На этом шаге он блокируется, так как его счетчик буферов достиг нуля и ждет предоставления новых буферов. На шаге 9 наступает тайм-аут хоста А, так как он до сих пор не получил подтверждения для сегмента 2. Этот сегмент посылается еще раз. В строке 10 хост подтверждает получение всех сегментов, включая 4-й, но отказывается предоставлять буферы хосту A. Такая ситуация невозможна в протоколах с фиксированным размером окна, описанных в главе 3. Следующий сегмент, посланный хостом B, разрешает хосту A передать еще один сегмент. Это произойдет тогда, когда у B появится свободное буферное пространство — скорее всего, потому, что потребитель транспортных услуг принял больше данных.

Компьютерные сети. 5-е издание - _332.jpg

Рис. 6.13. Динамическое выделение буферов. Стрелками показано направление передачи. Многоточие (...) означает потерянный сегмент

Проблемы при такой схеме выделения буферов в дейтаграммных сетях могут возникнуть при потере управляющего сегмента — что действительно может произойти. Взгляните на строку 16. Хост B выделил хосту A дополнительные буферы, но сообщение об этом было потеряно. Вот так неожиданность! Поскольку получение управляющих сегментов не подтверждается и, следовательно, управляющие сегменты не посылаются повторно по тайм-ауту, хост A теперь оказался блокированным всерьез и надолго. Для предотвращения такой тупиковой ситуации каждый хост должен периодически посылать управляющий сегмент, содержащий подтверждение и состояние буферов для каждого соединения. Это позволит, в конце концов, выбраться из тупика.

184
{"b":"639789","o":1}