![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
api-потоки, создание-разрушение [D6, WinXP]
Незнайка Винидиктович © (2009-03-29 18:25:00)Вот такая проблема случилась: Пишу подобие сокс5-сервера, с сипользование winapi-потоков, т.е. при старте запускаеться отдельный поток в котором крутиться бесконечный цикл с Accept, и как только есть подключившийся сокет, он создает поток и передает этот сокет туда... Так вот странность какая, что вродебы никаких общих переменных нету, никакой синхронизации нету(за её ненадобностью), т.е. все потоки существуют отдельно друг от друга. Так вот откудато берется ошибка памяти ((
В потоке примерно вот такая штука крутиться:
while True do
begin
FD_Zero(FDSet);
FD_Set(srv_sock,FDSet);
//åñëè åñòü êëèåíò, òî ïåðåäàåì ñîêåò â êëèåíòñêèé ïîòîê
Select(0,@FDSet,nil,nil,@timeout);
if FD_IsSet(srv_sock,FDSet) then
begin
accepted_sock:=Accept(srv_sock,@Addr,@addr_size);
CreateThread(nil, 0, @cli_thread, pointer(accepted_sock), 0, h);
end;
end;
Так вот кстати, как правельно разрушать потоки???
изнутри ExitThread(0); недостаточно? или как это правельно вообще делаеться?
Сергей М. (2009-04-05 14:56:00) [21]
> мимо (05.04.09 03:08) [69]
Ну не удалось и не удалось. Катастрофы не случится.
Автора пока заботят утечки, а не "удачность запуска потока"
мимо (2009-04-05 12:32:00) [22]Если Вас это успокоит и даст Вам возможность спать спокойно и с достоинством носить голубенький (С) - считайте, что я не знаю.
Palladin (2009-04-05 12:00:00) [23]То есть ты не знаешь. )
мимо (2009-04-05 11:44:00) [24]А как максимум - советую для разнообразия подумать самому. Мыслительный процесс он иногда полезен (по крайней мере - некоторым).
Palladin (2009-04-05 11:20:00) [25]А как максимум?
мимо (2009-04-05 11:12:00) [26]Как минимум - будет логическая ошибка, при которой программа преполагает запушенный поток, которого не будет.
Palladin (2009-04-05 09:45:00) [27]
> мимо (05.04.09 03:08) [69]
и что же будет если поток не удалось создать?
мимо (2009-04-05 03:08:00) [28]
> Closehandle(BeginThread(..)) - это даже ежу понятно..
Очень умно. А если поток не удалось создать?
Сергей М. (2009-04-04 22:57:00) [29]
> Хедл так и не понял как закрывать
closehandle(то что ты получил результатом вызова BeginThread)
> и вообще зачем, это переменная
Какая еще нахрен переменная ?
Closehandle(BeginThread(..)) - это даже ежу понятно..
мимо (2009-04-04 22:46:00) [30]Про Handle потока, оторый следует закрывать:
Handle есть описатель (читай указатель) на некую служебную информацию, которая система использует для управления потоком. Для каждого объекта (в данном случае потока) система ведет счетчик ссылок. Пока сей счетчик не равен 0 система не уничтожит (не освободит память) объект "поток" (структуру данных в памяти). Счетчик ссылок увеличивается при создании объекта (становится равным 1) и при вызове некоторых функций - таких как DuplicateHandle и уменшается при закрытии описателей. Соответственно, если не вызвать CloseHandle и не закрыть описатель потока - память не будет освобождена (от отбъекта "поток") до тех пор, пока не завершится все приложение (процесс). По сему, если этот описатель нигде больше не использется его следует сраз закрыть.
О завершении потоков:
Поток завершается вызовом функции ExitThread, TerminateThread либо выходом из функции потока (который приводит к вызову ExitThread с кодом завершения 0). Т.е. если явно не вызывать ExitThread то она будет вызвана после выполнения функции потока.
Важный момент: ExitThread НЕ возвращает управления вызывающей процедуре. Как следствие, в вашем примере, переменные типа string никогда не будут уничтожены (память, отведенная под них). Так как они являются управляемыми. Т.е., другими словами, "эпилог" функции не будет выполнен и локальные управляемые переменные не уничтожатся.
DVM (2009-04-04 14:26:00) [31]
> что без exitthread или endthread память как оказалось утекает
> меньше намного(почти не утекает), а с exitthread или endthread
> утекает ваще жостко, наверно решение где-то здесь?
Кто тебя вообще научил exitthread использовать. Поток должен умирать сам или по указке извне, но тоже сам. Т.е. поток должен периодически проверять флаг ПОРА ЗАКРУГЛЯТЬСЯ и если он ИСТИНА, то поток подчищаетвсе свои ресурсы и закругляется. Это единственный правильный способ. Все остальные способы будут приводить к утечкам.
Незнайка Винидиктович (2009-04-04 12:25:00) [32]Как я уже написал выше, что без exitthread или endthread память как оказалось утекает меньше намного(почти не утекает), а с exitthread или endthread утекает ваще жостко, наверно решение где-то здесь?
Полность утечку не удалось прекратить ((
Сергей М. (2009-04-02 14:30:00) [33]
> у ThreadId тип cadinal а не обжект? а CloseHandle(тут обжект)
Причем тут ThreadId ?
Это глобально уникальный идентификатор треда, а не его хэндл.
CloseHandle требует параметром хэндл треда, а не его идентификатор.
> убераем EndThread(0); и память не увеличивается ))
> вообще магия какая-то
"Магия" тут очень простая - вызывав EndThread ты потребовал от системы немедленного и безусловного завершения работы текущего треда, в то время как фактическая финализация переменной buf (читай - освобождение памяти, распределенной под строковые данные при IntToStr) произойдет лишь при любом трех условиях:
1. Выполнение оператора Exit
2. Выполнение оператора End
3. Необработанная в теле поточной ф-ции исключительная ситуация.
Незнайка Винидиктович (2009-04-02 14:19:00) [34]Хедл так и не понял как закрывать, и вообще зачем, это переменная, тем более она перезаписавается, что с неё будет ?
Незнайка Винидиктович (2009-04-02 14:18:00) [35]ООочень странная ситуация получаеться.
в примере(см.выше) делаем так:
function func(param: pointer): integer;
var
n: integer;
buf: string;
begin
n:=integer(param);
buf:=IntToStr(n);
Func:=0;
//EndThread(0);
end;
Т.е. убераем EndThread(0); и память не увеличивается ))
вообще магия какая-то, вот тебе и течка памяти )
Незнайка Винидиктович (2009-04-02 14:10:00) [36]так у ThreadId тип cadinal а не обжект? а CloseHandle(тут обжект) ... ну так это не обязатльно ты же говорил что не из-за этого утечка ?
Незнайка Винидиктович (2009-04-01 16:41:00) [37]Внял )) Но как ты говорил что утечка не из-за них ))
Сергей М. (2009-04-01 15:51:00) [38]
> так выше представленный код и есть полный
Так а какого же лешего ты не внял рекомендациям по закрытию хэндлов ?
Незнайка Винидиктович (2009-04-01 15:42:00) [39]так выше представленный код и есть полный... больше там ничего нету
это чисто экспиримент
Сергей М. (2009-04-01 12:54:00) [40]Приводи полный код ..