Карта сайта Kansoftware
НОВОСТИУСЛУГИРЕШЕНИЯКОНТАКТЫ
KANSoftWare

Определение полного приема сообщения в протоколе TCP: три подхода

Delphi , Синтаксис , Циклы

Протокол TCP (Transmission Control Protocol) является потоком байтов и не имеет Konzepta сообщений. Поэтому, есть только три способа для получателя узнать, когда полное сообщение было получено:

  1. Все сообщения фиксированной длины. Получатель просто читает столько байтов каждый раз.
  2. Отправитель отправляет длину сообщения перед самим сообщением. Получатель читает длину сначала, а затем столько байтов, сколько говорит длина.
  3. Отправитель отправляет уникальный terminator после каждого сообщения. Получатель читает до тех пор, пока не получен terminator.

Важно понимать, что нет 1:1 соотношения между отправкой и чтением на сокете TCP. Любая отдельная операция чтения может вернуть меньше байтов, чем запрошено, поэтому необходим цикл, чтобы убедиться, что все ожидаемые байты получены.

В втором случае необходим один цикл для чтения байтов длины сообщения, а затем другой цикл для чтения байтов самого сообщения.

Давайте рассмотрим примеры кода на Object Pascal (Delphi) для каждого из этих подходов.

Пример 1: Фиксированная длина сообщения

procedure FixedLengthMessage(var Socket: TSocket);
var
  Buffer: array[0..1023] of Byte;
  BytesRead: Cardinal;
begin
  SetLength(Buffer, 1024);
  BytesRead := 0;
  while BytesRead < 1024 do
  begin
    BytesRead := BytesRead + ReceiveSocket(Socket, @Buffer[BytesRead], 1024 - BytesRead, 0);
  end;
  // Обработка полученного сообщения
end;

Пример 2: Отправка длины сообщения

procedure LengthPrefixedMessage(var Socket: TSocket);
var
  LengthBuffer: array[0..3] of Byte;
  MessageBuffer: array[0..1023] of Byte;
  Length: Cardinal;
  BytesRead: Cardinal;
begin
  BytesRead := ReceiveSocket(Socket, @LengthBuffer[0], 4, 0);
  Length := (LengthBuffer[0] shl 24) or (LengthBuffer[1] shl 16) or (LengthBuffer[2] shl 8) or LengthBuffer[3];
  SetLength(MessageBuffer, Length);
  BytesRead := 0;
  while BytesRead < Length do
  begin
    BytesRead := BytesRead + ReceiveSocket(Socket, @MessageBuffer[BytesRead], Length - BytesRead, 0);
  end;
  // Обработка полученного сообщения
end;

Пример 3: Уникальный terminator

procedure TerminatorDelimitedMessage(var Socket: TSocket);
var
  Buffer: array[0..1023] of Byte;
  BytesRead: Cardinal;
  Terminator: array[0..2] of Byte;
begin
  SetLength(Buffer, 1024);
  SetLength(Terminator, 3);
  BytesRead := 0;
  while BytesRead < 1024 do
  begin
    BytesRead := BytesRead + ReceiveSocket(Socket, @Buffer[BytesRead], 1024 - BytesRead, 0);
    if CompareMem(@Buffer[BytesRead - 3], @Terminator[0], 3) = 0 then
      Break;
  end;
  // Обработка полученного сообщения
end;

В каждом из этих примеров мы используем цикл, чтобы гарантировать получение всех ожидаемых байтов. Важно выбрать подход, который лучше всего подходит для вашего конкретного использования протокола TCP.

Создано по материалам из источника по ссылке.

В данном контексте рассматриваются три подхода к определению полного приема сообщения в протоколе TCP: фиксированная длина сообщения, отправка длины сообщения и уникальный terminator, с примерами кода на Object Pascal (Delphi) для каждого из эти


Комментарии и вопросы

Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS




Материалы статей собраны из открытых источников, владелец сайта не претендует на авторство. Там где авторство установить не удалось, материал подаётся без имени автора. В случае если Вы считаете, что Ваши права нарушены, пожалуйста, свяжитесь с владельцем сайта.


:: Главная :: Циклы ::


реклама


©KANSoftWare (разработка программного обеспечения, создание программ, создание интерактивных сайтов), 2007
Top.Mail.Ru

Время компиляции файла: 2024-12-22 20:14:06
2025-01-29 03:46:16/0.0034182071685791/0