Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Сети";
Текущий архив: 2003.04.28;
Скачать: [xml.tar.bz2];

Вниз

Проблема: Поток обрабатывающий одно подключение в TServerSocket   Найти похожие ветки 

 
ole   (2003-03-04 05:06) [0]

Бывают моменты, когда поток, обрабатывающий обмен данными с клиентом, продолжает ожидать данные с закрытого соединения.
В результате программа, содержащая TServerSocket, начинает подвисать. Каким образом отключать подвисшие потоки?
Код потока привожу ниже:
procedure ClientExecute;
Var
Stream : TWinSocketStream;
Buffer : Array [0..8096] of byte;
Pack : TPacket Absolute Buffer;
N, T : Integer;
DataSize : Integer;
begin
N:=0;
Stream:=TWinSocketStream.Create(ClientSocket, TimeOut);
try
If Stream.WaitForData(TimeOut) Then
begin
N:=Stream.Read(Buffer,HeadSize);
While N<HeadSize Do
If Stream.WaitForData(TimeOut) Then
N:=N+Stream.Read(Buffer[N],HeadSize-N)
Else Break;
end;
//Заранее известно сколько байт в заголовке пакета.
//Поэтому ожидается именно HeadSize байт.
//Если считать в течении TimeOut не полчается -
//закрывается соединение
//Ниже аналогично считывается блок данных
If N=HeadSize Then
begin
DataSize:=Pack.Header.Len;
//длина данных содержится заголовке пакета
T:=Stream.Read(Buffer[N],DataSize);
While T<DataSize Do
If Stream.WaitForData(TimeOut) Then
T:=T+Stream.Read(Buffer[N+T],DataSize-T)
Else Break;
//пакет получен если T=DataSize;
If T=DataSize Then
begin
If Assigned(FClient.OnBadData)
Then FClient.FOnBadData(ClientSocket.RemoteAddress)
Else//иначе - обрабатываем пришедщий пакет
begin
Move(Buffer, FBuf, N+T);
//отдаем данные для обработки
FHeadSize:=N;
FDataSize:=T;
Synchronize(ParsePacket);
//синхронизируем с визуалом
//здесь выполняется разбор и обработка пакетов
end;
end;
end else
begin
Synchronize(Log);
//процедура записи в лог синхронизируется с визуалом
end;
End;//if
finally
Stream.Free;
ClientSocket.Close;
end;
end;

Что посоветуете?


 
ole   (2003-03-04 05:10) [1]

Сразу добавлю - это единовременное подключение.
Клиент передал данные и забыл о них.
Сервер получил и обработал.


 
Digitman   (2003-03-04 08:44) [2]

If Stream.WaitForData(TimeOut) Then
begin
............... // чтение из потока
end
else
...//ошибка таймаута, безусловно завершай исполнение метода Execute() !



p.s.
а вот эта строчка

Synchronize(ParsePacket);

сводит на нет все преимущество организации транспорта в доп.код.потоке !


 
ole   (2003-03-04 13:10) [3]

Диджитмэн:

Спасибо за ответ. И еще вопрос: разве нет необходимости закрывать открытый сокет?


> сводит на нет все преимущество организации транспорта в
> доп.код.потоке !

Я не могу не использовать синхронизацию. Здесь не так важно, что клиенты будут ожидать... здесь важно в принципе то, что возможно множество одновременных подключений. А в ParsePacket происходит вызов методов-событий родительского компонента (с помощью синхронизации я пытаюсь избежать двойного входения в процедуру)



 
Digitman   (2003-03-04 13:22) [4]


> разве нет необходимости закрывать открытый сокет


в данном конкретном случае - есть ... но - разве об этом речь шла вообще ?


> Я не могу не использовать синхронизацию. Здесь не так важно,
> что клиенты будут ожидать... здесь важно в принципе то,
> что возможно множество одновременных подключений. А в ParsePacket
> происходит вызов методов-событий родительского компонента
> (с помощью синхронизации я пытаюсь избежать двойного входения
> в процедуру)


а какая разница для "родительского компонента", в каком код.потоке происходит возбуждение одного из его событий ? Наверно, таки гораздо важней, в каком потоке оно обрабатываться будет ! А не возбуждаться)

Если уж исполнение запроса требует, по твоей логике, контекста осн.потока, то - разнеси существующий алгоритм из ParsePacket() таким образом, чтобы собственно парсинг пакета происходил в том же (доп.) потоке, а уж исполнение "разобранного и проверенного на целостность/корректность" полученного запроса синхронизировалось с осн.код.потоком


 
ole   (2003-03-06 11:01) [5]


> Digitman

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



Страницы: 1 вся ветка

Форум: "Сети";
Текущий архив: 2003.04.28;
Скачать: [xml.tar.bz2];

Наверх





Память: 0.46 MB
Время: 0.008 c
7-91579
BaDeVlad
2003-03-06 19:22
2003.04.28
Как программно свернуть все окна?


14-91505
NickBat
2003-04-10 16:32
2003.04.28
Про творчество...


1-91295
RavenD
2003-04-17 14:56
2003.04.28
Досрочное завершение цикла?


14-91541
Till
2003-04-11 14:46
2003.04.28
Чето не пойму почему нет установочного пакета?!


3-91217
Evgen
2003-04-10 15:54
2003.04.28
Работа с датами





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский