Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Работа с сетью в Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 23.09.2011, 17:10   #1
Crystallon
Форумчанин
 
Регистрация: 05.04.2010
Сообщений: 273
Вопрос Потеря части данных при отправке через TSocket

Доброго времени суток.
Отправляю строку размером в 65536 символов(прямо перед отправкой вывожу в tmemo length(sign_db[LP_i]) чтобы проверить что я наверняка передаю то что нужно и в целом виде, выдает как надо 65536):
Socket.SendText(sign_db[LP_i]);
Передача происходит от сервера к клиенту, клиент получает строку в которой только 3455 символов:
LP_rec:=Socket.ReceiveText;
Length(LP_rec) выводит 3455.
Содержимое изначальной строки(65536 символов) в прикрепленном txt файле(это кусок дампа памяти некоего процесса).
Собственно суть вопроса - в чем может быть причина обрезки строки?
Заранее спасибо за ответ.

http://rghost.ru/22730521
Crystallon вне форума Ответить с цитированием
Старый 23.09.2011, 17:20   #2
GunSmoker
Старожил
 
Регистрация: 13.08.2009
Сообщений: 2,581
По умолчанию

А ничего, что это не текст, а двоичные данные?
Опытный программист на C++ легко решает любые не существующие в Паскале проблемы.
GunSmoker вне форума Ответить с цитированием
Старый 23.09.2011, 17:26   #3
Crystallon
Форумчанин
 
Регистрация: 05.04.2010
Сообщений: 273
По умолчанию

Цитата:
Сообщение от GunSmoker Посмотреть сообщение
А ничего, что это не текст, а двоичные данные?
Еслиб это был обычный текст такого вообще не могло произойти, но даже так все равно часть этих данных передается нормально, почему с другой частью все иначе?
Crystallon вне форума Ответить с цитированием
Старый 23.09.2011, 17:29   #4
JUDAS
фонатик DELPHI
Форумчанин
 
Аватар для JUDAS
 
Регистрация: 14.01.2008
Сообщений: 714
По умолчанию

1. Через сокеты строки передавать не рекомендуется
2. рекомендую следующий алгоритм
- определить дамп памяти
- принять, что первые 6 байта передачи заголовок например 2 байта - сигнатура и 4 байта длина посылки
- отправлять строку дампом.
------------------
По сути, через приходит вся строка. Но на входе, не возможно определить её длину поэтому система и обрезает посылку.

Код:
var SEND : TSendRecord
       sign : word;
       length : integer;
     end;
      Dump : array of char;
begin
  S:= 'Эту строку нам нужно передать';
  SEND.length := 65535;
  SetLenGth(Dump,SEND.length );
  FillChar(Dump[0], SEND.length, 0);
  StrPCopy(Dump[0], S); 
  SEND.sign := $FF0E; // пусть это будет сигнатура
  Socket.SendBuf(SEND.sign,SEND.length +6);
  Finalize(Dump);
end;
на примёме

Код:
var RECV : TSendRecord
       sign : word;
       length : integer;
     end;
      Dump : array of char;
begin
  S.ReceiveBuf(Recv, SizeOf(TSendRecord));
  if RECV.sign<>$FF0E then >> ДОСВИДАНИЕ
  SetLenGth(Dump, RECV.length);
  S.ReceiveBuf(Dump[0], RECV.length);
  Finalize(Dump);
принимаете первые 6 байт и выуживаете длину.
Потом принимаете число байт равное SEND.length
----
Если потеря будет имметь место, попробуйте передать вашу посылку по частям , менее 64 кБ с попакетным раздроблением и сборкой.
95% сбоев и ошибок приложений, находится в полу метрах от монитора
JUDAS вне форума Ответить с цитированием
Старый 23.09.2011, 19:05   #5
Crystallon
Форумчанин
 
Регистрация: 05.04.2010
Сообщений: 273
По умолчанию

Хм, оригинально... Даже не знал что в сокетах есть такая абсурдная недоработка, а откуда вообще берется число полученных байт? Какой бы текст я не передавал получателю доходит только 3472 байта, почему именно 3472?
Crystallon вне форума Ответить с цитированием
Старый 23.09.2011, 20:36   #6
JUDAS
фонатик DELPHI
Форумчанин
 
Аватар для JUDAS
 
Регистрация: 14.01.2008
Сообщений: 714
По умолчанию

Цитата:
только 3472 байта
не могу сказать почему именно 3472 потому что не видно всего кода, но могу сказать с уверенностью, при написании серврера на сокетах, я передавал 34000 байт єто точно. Больших массивов я не передавал
95% сбоев и ошибок приложений, находится в полу метрах от монитора
JUDAS вне форума Ответить с цитированием
Старый 23.09.2011, 20:51   #7
mss
Заблокирован
 
Регистрация: 27.05.2010
Сообщений: 1,099
По умолчанию

Цитата:
не знал что в сокетах есть такая абсурдная недоработка
Нет там никакой "абсурдной недоработки".

Справку и документацию читать надо, а не пенять на кривизну сокетов

В ней черным по белому написано:

function SendText(const S: string): Integer; // function !!!!!!!!!!!!!!!!!!!!!!

SendText returns the number of bytes sent. Note that this may be less than the length of the string S if the socket is nonblocking.
mss вне форума Ответить с цитированием
Старый 02.10.2011, 21:46   #8
_Troy
Я не простой
Пользователь
 
Аватар для _Troy
 
Регистрация: 29.09.2011
Сообщений: 77
По умолчанию

За раз можно отправлять пакет длиной не более 65500 байт.
Знание бывает двух видов. Мы сами знаем предмет — или же знаем, где найти о нем сведения
_Troy вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Ошибка 200 при отправке данных )Игнат( Работа с сетью в Delphi 2 15.06.2011 19:43
Потеря данных при записи в Named Pipe (именованный канал) zvukoper Win Api 0 27.02.2011 20:02
Ошибка при отправке сообщений через SMTPClient BoT_T Работа с сетью в Delphi 6 26.09.2010 17:16
ComboBox проблема при отправке данных record222 Общие вопросы Delphi 1 31.03.2010 16:26
Потеря данных при изменении рамера раздела Drandulet Софт 5 06.07.2008 07:52