Nets2010 (1131259), страница 21
Текст из файла (страница 21)
Разбиение потока битов на кадры - задача не простая. Один из способов - делать паузу между битами разных кадров. Однако в сети, где нет единого таймера, нет гарантии, что эта пауза всегда будет одинаковой, или, наоборот, не появится новая пауза там, где ее не должно было быть.
Так как методы, использующие временные задержки, не надежны, применяются другие методы. Здесь мы рассмотрим четыре основных метода:
-
счетчик символов
-
вставка специальных стартовых и конечных символов
-
вставка стартовых и концевых битов
-
нарушение кодировки на физическом уровне
Первый метод (счетчик символов)показан на рисунке 3-3. В начале каждого кадра указывают, сколько символов в кадре. При приеме кадра вновь подсчитывают число принятых символов. Если число полученных символов отлично от ожидаемого числа, то этот факт воспринимают как ошибку. Однако этот метод имеет существенный недостаток: счетчик символов может быть искажен при передаче. Тогда принимающая сторона не сможет обнаружить границы кадра. Даже обнаружив несовпадение контрольных сумм, принимающая сторона не сможет сообщить передающей, какой кадр надо переслать и сколько символов пропало. Этот метод сейчас используется редко.
Рисунок 3-3. Поток символов: (а) без ошибок; (b) с одной ошибкой
Второй метод (вставка специальных стартовых и конечных символов)построен на вставке специальных символов. Обычно для этого используют последовательность символов DLE STX для начала кадра и DLE ETX для конца кадра. DLE (Data Link Escape), STX (Start TeXt), ETX (End TeXt) – это специальные символы, имеющие специальную кодировку. При этом методе, если даже была потеряна граница текущего кадра, нужно просто найти ближайшую последовательность DLE STX или DLE ETX. Однако здесь есть одна опасность: при передаче чисел или программы в объектном коде такие последовательности могут уже содержаться в передаваемых данных. Для решения этой проблемы используют прием экранирования: каждая последовательность DLE или STX просто дублируется в передаваемых данных. Поэтому, если при приеме есть два последовательных DLE, то один удаляется. Этот метод проиллюстрирован на рисунке 3-4.
Рисунок 3-4. Метод экранирования
Основным недостатком только что рассмотренного метода является то, что он жестко связан с размером байта и конкретным методом кодировки символов - ASCII. По мере развития сетей эта связь становилась все более и более обременительной. Кроме этого, на стороне отправителя надо было просматривать кадр, чтобы обнаружить недопустимые последовательности.
Был предложен иной прием, позволяющий использовать любое число битов на символ и любую кодировку. (вставка стартовых и концевых битов)Его идея состоит в том, что каждый кадр начинается и заканчивается специальным флаг-байтом: 01111110. Чтобы избежать аналогичной последовательности, внутри кадра поступают следующим образом. Посылающая сторона, встретив последовательно 5 единиц, обязательно вставит 0. Принимающая сторона, приняв 5 последовательных единиц, обязательно удалит следующий за ними 0. Таким образом, если в передаваемых данных встретится конфигурация флаг-байта, то она будет преобразована в конфигурацию 011111010. Этот метод иллюстрирует рисунок 3-5. Этот метод прозрачен для сетевого уровня так же, как и метод вставки байтов.
Рисунок 3-5. Замена шестой единицы нулем
Таким образом, кадр легко может быть распознан по флаг-байту. Если граница очередного кадра по какой-то причине была потеряна, то все что надо делать – «ловить» ближайший флаг-байт.
Последний метод - нарушение кодировки используется там, где применяется специальная кодировка битов на физическом уровне. Например, пусть для передачи одного бита используется два импульса. «1» кодируется как переход «высокое-низкое», «0» - как переход «низкое-высокое». Сочетания «низкое-низкое» или «высокое-высокое» не используются для передачи данных. Их и используют для границ кадра. Так делают в стандарте IEEE 802 для ЛВС, который мы рассмотрим позже.
На практике используют, как правило, комбинацию этих методов. Например, счетчик символов с одним из выше перечисленных. Тогда, если число символов в кадре совпадает с кодировкой границы кадра, кадр считается переданным правильно.
3.1.3. Обнаружение ошибок
Решив проблему разбиения на кадры, мы приходим к следующей проблеме: как обеспечить, чтобы кадры попадали на сетевой уровень в надлежащей последовательности? Если для отправляющей стороны все равно, в какой последовательности поступают кадры, то этой проблемы нет. Например, если нам нужен сервис без уведомления и без соединения. Однако как быть, если нам нужен сервис с уведомлением и с соединением?
Для решения этой проблемы устанавливают обратную связь между отправителем и получателем в виде кадра подтверждения. Если кадр-подтверждение несет положительную информацию, то считается, что переданные кадры прошли нормально, если же в нем сообщение об ошибке, то переданные кадры надо передать заново.
Однако возможны ситуации, когда из-за ошибок в канале кадр исчезнет целиком. В этом случае получатель не будет никак реагировать, а отправитель будет сколь угодно долго ждать подтверждения. Для решения этой проблемы на канальном уровне вводят таймеры. Когда передается очередной кадр, то одновременно устанавливается таймер на определенное время. Этого времени должно хватать на то, чтобы получатель получил кадр и отправил уведомление, а отправитель получил его.
Если отправитель не получит уведомление раньше, чем истечет время, установленное на таймере, то он будет считать, что кадр потерян и повторит его еще раз.
Однако если кадр-подтверждение был утерян, то вполне возможно, что один и тот же кадр получатель получит дважды. Как быть? Для решения этой проблемы каждому кадру присваивают порядковый номер. С помощью этого номера получатель может обнаружить дубли.
Итак, таймеры и нумерация кадров - основные средства на канальном уровне, обеспечивающие доставку каждого кадра до сетевого уровня в единственном экземпляре и в нужном порядке.
3.1.4. Управление потоком
Другая важная проблема, которую надо решать на канальном уровне - управление потоком. Вполне может случиться, что отправитель будет посылать кадры столь часто, что получатель не будет успевать их обрабатывать. Это может произойти, если, например, машина-отправитель более мощная или загружена слабее, чем машина-получатель.
Для борьбы с такими ситуациями вводят специальный механизм управления потоком. Этот механизм предполагает обратную связь между отправителем и получателем, которая позволяет им урегулировать темп передачи.
Существует много схем управления потоком, но все они в основе своей используют следующий сценарий. Прежде чем отправитель начнет передачу, он спрашивает у получателя, сколько кадров тот может принять. Получатель сообщает ему определенное число. Отправитель, после того как передаст это число кадров, должен приостановить передачу и спросить у получателя еще раз, сколько кадров тот может принять, и т.д. Позднее на примерах мы познакомимся с конкретными механизмами управления потоком.
Раздел 3.3. Простейшие протоколы канала данных
Рассмотрение протоколов уровня канала данных мы начнем с нескольких предположений. Будем предполагать, что физический уровень, уровень канала данных, сетевой уровень – реализованы в виде независимых процессов, взаимодействующих с помощью передачи сообщений.
Также мы предположим, что есть две машины: А и В. У машины А есть бесконечно длинный набор данных, который надо передать машине В с помощью надежного сервиса, ориентированного на соединение. Передача всегда происходит от А к В, хотя позднее мы допустим одновременную передачу от В к А. Также будем предполагать, что если канальный уровень на машине А запрашивает данные для передачи от сетевого уровня, то они всегда есть и нет задержки на их подготовку.
Канальный уровень рассматривает данные, которые он получает от сетевого, как неструктурированные, несмотря на то, что там есть хотя бы заголовок сетевого уровня. Все эти данные должны быть переданы равнозначному сетевому уровню. Когда канальный уровень получает пакет, он погружает его в кадр, добавляя заголовок и концевик. Этот кадр затем передается по физическому уровню. Будем предполагать, что есть две библиотечные процедуры: from_physical_layer - для получения кадра с физического уровня, и to_physical_layer - для передачи кадра на физический уровень. Предполагаем, что вычисление и добавление контрольных сумм происходит аппаратно.
Изначально получатель просто ожидает, ничего не предпринимая, наступления какого-либо события. В наших примерах это будет выражаться в вызове процедуры wait_for_event(&event), где параметр event возвращает информацию о произошедшем событии. Ясно, что в действительности никто не будет ожидать в цикле (будут использованы прерывания), но мы для простоты будем считать так.
Когда кадр поступает к получателю, контрольная сумма вычисляется аппаратно. Если она неверна, то канальному уровню сообщается: event=cksum_err. Если кадр поступил без повреждений, то канальный уровень информируется так: event=frame_arrivel.
Как мы уже отмечали, для того чтобы обнаруживать случаи потери кадров, уровень канала, отправляя кадр, должен устанавливать таймер. Если подтверждение не придет раньше, чем истечет время таймера, то считается, что кадр не дошел. В этом случае event=timeout. Процедуры start_timer и stop_timer используют для пуска и остановки таймера. Процедуру запуска таймера можно вызывать, не ожидая окончания предыдущего запуска. Подобное обращение будет означать перезапуск таймера на новый интервал.
Процедуры enable_network_layer и disable_network_layer используются в сложных протоколах, когда предполагается, что на сетевом уровне нет пакетов для передачи. Когда канальный уровень разрешит сетевому уровню снова передавать пакеты, сетевой информирует об этом событием event=network_layer_ready. Если канальный уровень выполнил процедуру disable_network_layer, то event=network_layer_ready может и не последовать. Таким способом канальный уровень может управлять потоком от сетевого уровня.
Симплекс-протокол без ограничений.
На рисунке 3-9 представлен простейший протокол канального уровня. Данные передаются только в одном направлении. Получатель и отправитель всегда готовы к отправке и получению данных. Время обработки данных игнорируется. Предполагается, что буфер неограниченного размера. Данные в канале не теряются и не искажаются.
Рисунок 3-9. Симплексный протокол канального уровня
Симплексный старт-стопный протокол.
Теперь снимем одно из ограничений предыдущего протокола - способность сетевого уровня обрабатывать поступающие данные сколь угодно быстро. Все остальные предположения остаются в силе: канал абсолютно надежный, трафик однонаправленный.
Основная проблема - как предотвратить ситуацию, когда отправитель «заваливает» данными получателя. Если получателю требуется время Δt, чтобы исполнить from_physical_layer плюс to_network_layer, то отправитель должен передавать данные со средней скоростью один кадр в Δt.
Решением такой проблемы может быть введение коротких специальных служебных сообщений. Получатель, получив один или несколько кадров, отправляет отправителю короткий специальный кадр, означающий, что отправитель может передавать следующий. Это так называемый старт-стопный протокол, показанный на рисунке 3-10.
Рисунок 3-10. Однонаправленный старт-стопный протокол канального уровня
Симплексный протокол для канала с шумом.
Основная проблема при передаче состоит в том, что кадр с подтверждением о получении может потеряться целиком. Как отличить кадр, переданный первый раз, от кадра, переданного повторно?
Одно из очевидных решений - нумерация передаваемых кадров. Однако сколько места отводить под эту нумерацию? Поскольку проблема различения стоит для кадров m и m+1, то достаточно одного разряда. 0 - для только что посланного кадра и 1 - для следующего ожидаемого. Все кадры, не содержащие корректной нумерации, просто сбрасываются при приеме.
На рисунке 3-11 показана программа для этого варианта протокола.