Protokół Stop-and-Wait

Prosty mechanizm kontroli przepływu oparty na potwierdzeniach z timeout i retransmisją.

Podstawowe Wyzwanie: Niezawodna Komunikacja przez Niezawodny Kanał

Główną misją Warstwy Łącza Danych jest zapewnienie niezawodnego transferu danych między dwoma bezpośrednio połączonymi urządzeniami. Brzmi to prosto, ale medium fizyczne łączące je – czy to kabel miedziany, światłowód, czy otwarte powietrze – jest z natury niedoskonałe. Sygnały mogą być zakłócane przez szum elektryczny, tłumione na odległość lub po prostu gubione z powodu chwilowych interferencji. To tworzy dwa fundamentalne problemy:

  1. Uszkodzone Ramki: Skąd odbiorca ma wiedzieć, czy dane, które otrzymał, są takie same jak dane wysłane przez nadawcę?
  2. Utracone Ramki: Jeśli ramka (lub jej potwierdzenie) całkowicie zniknie, skąd nadawca ma wiedzieć, że musi ją wysłać ponownie?

Najprostszą możliwą odpowiedzią na te problemy jest Protokół Stop-and-Wait. Jest to fundamentalny protokół . Chociaż rzadko używany dzisiaj w czystej postaci ze względu na swoją nieefektywność, zrozumienie go jest absolutnie kluczowe, ponieważ wszystkie nowoczesne, zaawansowane protokoły, takie jak TCP, są zbudowane na jego podstawowych zasadach potwierdzeń i limitów czasu.

Główna Zasada Stop-and-Wait

Logikę protokołu można sprowadzić do jednej, nienaruszalnej zasady dla nadawcy:

"Wyślij jedną ramkę, a następnie ZATRZYMAJ SIĘ i CZEKAJ na pozytywne potwierdzenie, zanim wyślesz następną."

Ta prosta zasada zapewnia zarówno kontrolę przepływu (zapobiegając zalaniu wolnego odbiorcy przez szybkiego nadawcę), jak i kontrolę błędów (zapewniając retransmisję utraconych lub uszkodzonych ramek). Jest jak prowadzenie niezwykle ostrożnej rozmowy, w której wypowiadasz jedno zdanie, a następnie czekasz, aż druga osoba wyraźnie potwierdzi, że usłyszała je poprawnie, zanim przejdziesz dalej.

Stop-and-Wait w Akcji: Scenariusz Idealny

Najpierw przeanalizujmy idealny scenariusz, w którym kanał działa bez zarzutu, a żadne dane nie są tracone ani uszkadzane.

  1. Krok 1: Nadawca Wysyła Ramkę: Nadawca (Węzeł A) pobiera pierwszą porcję danych, zamyka ją w ramce z numerem sekwencyjnym 0 i wysyła ją do odbiorcy (Węzeł B).
  2. Krok 2: Nadawca Uruchamia Licznik Czasu: Natychmiast po wysłaniu ramki, Węzeł A uruchamia . Ten licznik działa jak zabezpieczenie.
  3. Krok 3: Odbiorca Otrzymuje Ramkę: Po pewnym opóźnieniu propagacji, Węzeł B otrzymuje Ramkę 0. Sprawdza FCS, aby upewnić się, że ramka nie jest uszkodzona.
  4. Krok 4: Odbiorca Wysyła Potwierdzenie: Ponieważ ramka jest prawidłowa, Węzeł B odsyła ramkę potwierdzającą (ACK). ACK ten określa numer sekwencyjny następnej ramki, której oczekuje. W tym przypadku, skoro poprawnie odebrał Ramkę 0, wysyła ACK 1.
  5. Krok 5: Nadawca Otrzymuje ACK: Węzeł A otrzymuje ACK 1 przed wygaśnięciem swojego licznika. To potwierdza, że Ramka 0 dotarła bezpiecznie. Węzeł A zatrzymuje licznik.
  6. Krok 6: Powtórzenie Cyklu: Teraz, gdy Ramka 0 została potwierdzona, Węzeł A może wysłać następną ramkę w sekwencji, Ramkę 1, i cykl rozpoczyna się od nowa.

Obsługa Awarii: Mechanizm Limitu Czasu (Timeout)

Prawdziwy świat nie jest doskonały. Ramki mogą zaginąć. Licznik czasu jest jedynym sposobem, w jaki nadawca może wykryć ten typ awarii.

Scenariusz 1: Utracona Ramka Danych

  1. Nadawca przesyła Ramkę 0 i uruchamia swój licznik czasu.
  2. Ramka ginie w tranzycie z powodu nagłego zakłócenia w kanale.
  3. Odbiorca, Węzeł B, nigdy nic nie otrzymuje. Czeka pasywnie.
  4. Nadawca, Węzeł A, czeka. Żadne ACK nie nadchodzi.
  5. Licznik czasu nadawcy wygasa. Z perspektywy nadawcy jest to jednoznaczny sygnał, że coś poszło nie tak.
  6. Zakładając, że ramka została utracona, nadawca pobiera kopię Ramki 0 ze swojego bufora i retransmituje ją, ponownie uruchamiając licznik.

Licznik jest rdzeniem mechanizmu „Automatycznego Żądania Powtórzenia”. Jest wyzwalaczem automatycznego ponownego wysyłania utraconych danych.

Scenariusz 2: Utracona Ramka Potwierdzająca (ACK)

Ten scenariusz jest bardziej subtelny, ale równie ważny do obsłużenia. Co, jeśli ramka z danymi dotrze bezpiecznie, ale potwierdzenie zaginie w drodze powrotnej?

  1. Nadawca przesyła Ramkę 0 i uruchamia swój licznik czasu.
  2. Odbiorca poprawnie odbiera Ramkę 0 i odsyła ACK 1.
  3. Ramka ACK 1 ginie w tranzycie.
  4. Nadawca, nieświadomy, że dane dotarły, nadal czeka.
  5. Licznik czasu nadawcy wygasa. Tak jak poprzednio, nadawca nie ma sposobu, by wiedzieć, dlaczego ACK nie dotarło. Musi przyjąć najgorszy scenariusz: że oryginalna ramka z danymi została utracona.
  6. Nadawca retransmituje Ramkę 0.

Rozwiązanie Problemu Duplikatów: Siła Jednego Bita

Scenariusz „Utraconego ACK” tworzy nowy problem: odbiorca otrzyma teraz zduplikowaną kopię Ramki 0. Gdyby po prostu zaakceptował ten duplikat i przekazał go do warstwy sieciowej, strumień danych zostałby uszkodzony (np. zdanie w pliku mogłoby pojawić się dwa razy).

Stop-and-Wait rozwiązuje to za pomocą najprostszej możliwej formy numeracji sekwencyjnej. Potrzebuje tylko jednego bita do naprzemiennego oznaczania ramek, zazwyczaj 0 i 1.

Jak Działa 1-bitowa Numeracja Sekwencyjna

Konwersacja teraz obejmuje sprawdzanie numerów sekwencyjnych:

  1. Nadawca wysyła Ramkę 0.
  2. Odbiorca otrzymuje Ramkę 0, odsyła ACK 1 i teraz oczekuje Ramki 1.
  3. ACK 1 zostaje utracony. Licznik czasu nadawcy wygasa.
  4. Nadawca retransmituje Ramkę 0.
  5. Odbiorca otrzymuje zduplikowaną Ramkę 0. Sprawdza jej numer sekwencyjny. Oczekiwał Ramki 1, a otrzymał Ramkę 0.
  6. Odbiorca wie teraz, że to duplikat. Odrzuca zduplikowaną ramkę, ale jako pomocny gest, ponownie wysyła ostatnie udane potwierdzenie, ACK 1, ponieważ nadawca najwyraźniej wciąż na nie czeka.

Ten niewielki, 1-bitowy numer sekwencyjny wystarcza, aby uczynić protokół odpornym zarówno na utratę ramek danych, jak i utratę ACK, zapewniając, że każda ramka danych zostanie dostarczona do wyższej warstwy dokładnie raz.

Analiza: Przytłaczająca Niewydajność Stop-and-Wait

Chociaż prosty i niezawodny, protokół Stop-and-Wait jest niesamowicie nieefektywny, szczególnie w nowoczesnych, szybkich i dalekosiężnych sieciach. Jego wydajność nie jest ograniczona przepustowością łącza, ale jego opóźnieniem propagacji.

Przykład z Prawdziwego Świata: Światłowód Transatlantycki

Rozważmy realistyczny scenariusz: wysyłanie danych przez dedykowane łącze światłowodowe między Warszawą a Nowym Jorkiem.

  • Przepustowość łącza (R): 1 Gigabit na sekundę (1×1091 \times 10^9 bps).
  • Odległość (d): Około 7,000 km.
  • Prędkość propagacji (v): Prędkość światła w światłowodzie to około 2×1082 \times 10^8 m/s.
  • Rozmiar ramki (L): Standardowa ramka 1,500 bajtów (12,000 bitów).

Najpierw obliczmy dwa krytyczne składniki czasowe:

  1. Czas Transmisji (Ttx)(T_{tx}): Jak długo trwa „wypchnięcie” wszystkich bitów jednej ramki na łącze.

    Ttx=Rozmiar Ramki (L)Przepustowosˊcˊ (R)=12,000 bitoˊw1×109 bps=0.000012 sekundy=12 µsT_{tx} = \frac{\text{Rozmiar Ramki (L)}}{\text{Przepustowość (R)}} = \frac{12,000 \text{ bitów}}{1 \times 10^9 \text{ bps}} = 0.000012 \text{ sekundy} = 12 \text{ µs}

  2. Opóźnienie Propagacji (Tp)(T_p): Jak długo pierwszy bit podróżuje z jednego końca na drugi.

    Tp=Odległosˊcˊ (d)Prędkosˊcˊ (v)=7,000,000 m2×108 m/s=0.035 sekundy=35,000 µsT_p = \frac{\text{Odległość (d)}}{\text{Prędkość (v)}} = \frac{7,000,000 \text{ m}}{2 \times 10^8 \text{ m/s}} = 0.035 \text{ sekundy} = 35,000 \text{ µs}

  3. Czas Podróży w Obie Strony (RTT): Czas potrzebny na dotarcie ramki i powrót ACK. Zakładamy, że ACK jest bardzo małe, więc jego czas transmisji jest pomijalny. RTT jest zdominowany przez dwukrotny czas podróży.

    RTT2×Tp=2×35,000 µs=70,000 µsRTT \approx 2 \times T_p = 2 \times 35,000 \text{ µs} = 70,000 \text{ µs}

Obliczanie Wykorzystania Łącza

Nadawca spędza 12 µs12 \text{ µs} na nadawaniu i 70,000 µs70,000 \text{ µs} na czekaniu. Wykorzystanie łącza (U)(U) to ułamek czasu, w którym łącze jest faktycznie używane do wysyłania danych:

U=TtxTtx+RTT=1212+7000012700120.000171U = \frac{T_{tx}}{T_{tx} + RTT} = \frac{12}{12 + 70000} \approx \frac{12}{70012} \approx 0.000171

Wykorzystanie Łącza: 0.0171%

Ten wynik jest oszałamiający. Mamy łącze światłowodowe 1 Gb/s: superautostradę danych, ale protokół Stop-and-Wait zmusza je do bycia bezczynnym przez 99.9829% czasu. Nasza efektywna przepustowość to nie 1 Gb/s, ale zaledwie 1 Gb/s×0.000171171 kbps1 \text{ Gb/s} \times 0.000171 \approx 171 \text{ kbps}, wolniej niż stare domowe połączenie internetowe z początku wieku.

Wnioski: Niezbędny, lecz Niewystarczający Krok

Protokół Stop-and-Wait jest doskonałym narzędziem teoretycznym do wprowadzenia koncepcji niezawodności w warstwie łącza. Zapewnia on bezbłędną kontrolę przepływu oraz, po dodaniu numerów sekwencyjnych, solidną kontrolę błędów. Jest prosty, łatwy do zrozumienia i w pełni niezawodny.

Jednak jego praktyczna wydajność jest nie do przyjęcia dla prawie wszystkich nowoczesnych zastosowań. Okres „oczekiwania” nieodłącznie związany z jego konstrukcją jest wąskim gardłem, którego nie można przezwyciężyć bez zmiany podstawowej zasady. Ta głęboka nieefektywność jest właśnie powodem, dla którego opracowano bardziej zaawansowane techniki, mianowicie Protokoły Przesuwnego Okna, takie jak Go-Back-N i Powtórzenie Selektywne. Budują one na solidnym fundamencie potwierdzeń i limitów czasu Stop-and-Wait, ale dodają kluczową zdolność do „wypełniania potoku”, utrzymując kanał zajęty i uwalniając prawdziwy potencjał nowoczesnych sieci.

    Protokół Stop-and-Wait | Teleinf Edu