Форум: "Сети";
Текущий архив: 2006.12.24;
Скачать: [xml.tar.bz2];
Вниззакрытие сокета другого потока Найти похожие ветки
← →
Ketmar © (2006-07-26 19:16) [0]суть такая: есть n потоков, которые активно читают/пишут в совкеты. прокси-сервер, короче. %-) сокеты -- блокирующие.
в один печальный момент надо пришибить все эти потоки. как можно быстрее. сейчас я просто закрываю все сокеты, с которыми работают эти потоки (из отдельного потока-наблюдателя %-). вроде работает (за исключением сокета, который ожидает в connect() -- эти долго-долго думают %-(( ).
понимаю, что варварство, но ничего более умного сочинить не могу.
собственно, вопрос в том, наступал ли кто-то на грабли при таком жёстком изврате? или никто подобный невежливый код не пишет?
зыж нет, я в курсе, что есть неблокирующие сокеты. огромная просьба меня не тыкать в них -- интересно именно для блокирующих.
(не совсем уверен, что это не в WinAPI надо было...)
← →
Ketmar © (2006-07-26 19:20) [1]тьфу. пока отправлял -- понял, что натупил. данные ходят небольшими порциями, и никто не мешает между порциями проверять любые флажки и условия.
однако для сокета, который "слушает", вижу только одно решение -- прекратить "слушать" в блокирующем режиме. (то есть, не "слушать", конечно, а "принимать"). придётся делать select() и вызывать accept() только если кто-то пришёл. не хочется. но, видимо, других вариантов нет -- кроме кривых хаков. %-(
← →
Медведъ (2006-07-26 19:55) [2]Windows имеет замечательный API, используй его
какой смысл мучать блокируюший режим, для прокси сервера вполне достаточно одного транспортного потока
← →
Ketmar © (2006-07-26 20:56) [3]>Медведъ (26.07.06 19:55) [2]
а я как, по-твоему, сокеты юзаю, если не через winsock-API? %-)
а с одним неудобно. во-первых, я не люблю неблокирующие сокеты, во-вторых -- зачем писать транспортный диспетчер, если с этим отлично справляется сама винда при использовании потоков? больше 20-24 потоков у меня быть не может по-определению, не вижу смысла усложнять программу. %-) реально обычно активно 5-6 потоков. редко когда 8. проксь-то исключительно для личного использования.
более того: неблокирующий режим считаю извращением, рождённым в больных мозгах программеров некрософта. %-)
← →
tesseract © (2006-07-26 22:02) [4]Удалено модератором
Примечание: Оффтоп...
← →
Ketmar © (2006-07-27 00:26) [5]Удалено модератором
Примечание: Оффтоп...
← →
Медведъ (2006-07-27 09:35) [6]Удалено модератором
Примечание: Оффтоп...
← →
Ketmar © (2006-07-27 10:13) [7]Удалено модератором
Примечание: Оффтоп...
← →
Медведъ (2006-07-27 14:35) [8]Удалено модератором
Примечание: Все что ниже удалено - Оффтоп...
← →
Сергей М. © (2006-07-27 15:02) [9]Удалено модератором
← →
Медведъ (2006-07-27 16:08) [10]Удалено модератором
← →
Сергей М. © (2006-07-27 16:13) [11]Удалено модератором
← →
DiamondShark © (2006-07-28 00:45) [12]
> Ketmar © (26.07.06 19:20) [1]
> однако для сокета, который "слушает", вижу только одно решение
> -- прекратить "слушать" в блокирующем режиме. (то есть,
> не "слушать", конечно, а "принимать"). придётся делать select()
> и вызывать accept() только если кто-то пришёл. не хочется.
> но, видимо, других вариантов нет -- кроме кривых хаков.
> %-(
Зочем?
Вот примерчик накатал:
function AcceptThread(Param: Pointer): Integer;
const
hello: PChar = "Preved krosavcheg!";
var
listenSocket: TSocket;
client: TSocket;
addr: TSockAddrIn;
len: Integer;
error: Integer;
errorText: String;
begin
Result := 0;
listenSocket := TForm1(Param).FListenSocket;
repeat
len := sizeof(addr);
client := accept(listenSocket, @addr, @len);
if client = INVALID_SOCKET then break;
send(client, hello^, StrLen(hello), 0);
closesocket(client);
until false;
error := WSAGetLastError;
errorText := SysErrorMessage(error);
end;
procedure TForm1.StartListen;
var
Thread: THandle;
ThreadId: DWORD;
addr: TSockAddrIn;
begin
FListenSocket := socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
WinSockCheck(FListenSocket <> INVALID_SOCKET);
addr.sin_family := AF_INET;
addr.sin_port := htons(1024);
addr.sin_addr.S_addr := htonl(INADDR_ANY);
bind(FListenSocket, addr, sizeof(addr));
listen(FListenSocket, SOMAXCONN);
Thread := BeginThread(nil, 0, AcceptThread, self, 0, ThreadId);
CloseHandle(Thread);
end;
procedure TForm1.StopListen;
begin
if FListenSocket <> INVALID_SOCKET then
begin
closesocket(FListenSocket);
FListenSocket := INVALID_SOCKET;
end
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
StartListen;
end;
procedure TForm1.Button2Click(Sender: TObject);
begin
StopListen;
end;
При вызове closesocket(FListenSocket) accept возвращает WSAEINTR и замечательно завершается.
← →
Медведъ (2006-07-28 10:10) [13]Удалено модератором
← →
Сергей М. © (2006-07-28 10:21) [14]Удалено модератором
← →
Ketmar © (2006-07-28 10:44) [15]Удалено модератором
← →
Медведъ (2006-07-28 14:17) [16]Удалено модератором
← →
Сергей М. © (2006-07-28 14:29) [17]
> Медведъ (28.07.06 14:17) [16]
Асинхронность автора сего поста, заметь, интересует меньше всего.
← →
Ketmar © (2006-07-28 14:36) [18]>Медведъ (28.07.06 14:17) [16]
цитирую себя же из [0]:
"я в курсе, что есть неблокирующие сокеты. огромная просьба меня не тыкать в них".
а про асинхронность вообще речи даже не начиналось.
← →
Медведъ (2006-07-28 14:41) [19]Удалено модератором
← →
Ketmar © (2006-07-28 16:16) [20]Удалено модератором
← →
Медведъ (2006-07-28 16:43) [21]Удалено модератором
← →
Ketmar © (2006-07-28 16:52) [22]Удалено модератором
← →
Медведъ (2006-07-28 17:24) [23]Удалено модератором
← →
Ketmar © (2006-07-28 18:08) [24]Удалено модератором
← →
Verg © (2006-07-29 12:16) [25]
> вроде работает (за исключением сокета, который ожидает в
> connect() -- эти долго-долго думают %-(( ).
И что? При connect-е "долго думают"?
Для блокирующего режима убийство сокета (из другого потока) - есть единственное универсальное средство прервать его думы по любому поводу.
> придётся делать select() и вызывать accept() только если
> кто-то пришёл. не хочется.
Эка невидаль или что, каприз?
← →
Ketmar © (2006-07-30 13:39) [26]>Verg © (29.07.06 12:16) [25]
да. при медленной сети сокет в connect() уходит за пивом.
а делать лишний select() не хочу, потому что и так нечто подобное делает accept(). дублирование кода. %-)
← →
Медведъ (2006-07-31 10:47) [27]Удалено модератором
← →
Ketmar © (2006-07-31 15:56) [28]Удалено модератором
← →
Медведъ (2006-07-31 20:06) [29]Удалено модератором
Страницы: 1 вся ветка
Форум: "Сети";
Текущий архив: 2006.12.24;
Скачать: [xml.tar.bz2];
Память: 0.52 MB
Время: 0.041 c