![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
Чем вызвана ошибка Thread Creation error: No enought storage ... [D6, NT4]
Aleksandr © (2002-07-09 12:58:00)Я предполагаю, что ошибка связана с Coinitialize.
Суть такова:
Есть базовый поток, в котором вызывается Coinitialize(nil) при создании и Couninitialize в дестракторе. Вызываются эти функции, потому что в потомках этого потока (разных, иногда существующих в нескольких экземплярах каждый) используются TADOQuery (в базовом его нет). И по истечении какого-то периода работы программа начинает выдавать указанную ошибку. Может, причина в том, что Coinitialize следует вызывать только в самих потомках?
Digitman (2002-07-09 15:59:00) [1]Нет, не повлияет
Aleksandr (2002-07-09 15:32:00) [2]Большое спасибо! Только базовый DoExecute не abstract, а просто virtual - когда она писалась, такого еще не было. А потомок - override. Надеюсь, это не повлияет?
Digitman (2002-07-09 14:42:00) [3]если
TShowProgressThread.DoExecute; virtual; abstract;
а
TQueryThread.DoExecute; override;
то
procedure TQueryThread.DoExecute;
begin
Coinitialize(nil);
try
DoSomething;
finally
Couninitialize
end
end;
Aleksandr (2002-07-09 14:36:00) [4]Или вообще мона сделать так:
procedure TQueryThread.DoExecute;
begin
Coinitialize(nil);
try
DoSomething;
finally
Couninitialize
end
end;
Execute у него по-прежнему отсутствует, вместо него базовый:
procedure TShowProgressThread.Execute;
begin
DoSomething;
DoExecute;
DoSomething
end;
Aleksandr (2002-07-09 14:29:00) [5]Ничего не понимаю... Так где мне вызывать Coinitialize - у базового потомка TShowProgressThread или полностью перекрывать его Execute в его потомках и вызывать в них? :(
Digitman (2002-07-09 13:56:00) [6]И правильно делал "предыдущий автор") ... Coinitialize/CoUninitialize() нужно вызывать ТОЛЬКО в переопределенном вирт.методе TThread.Execute
Aleksandr (2002-07-09 13:30:00) [7]Просто у меня глобальная проблема в организации программы предыдущим автором. Он в базовом потоке закрывал Execute, делая его выполнение следующим образом:
procedure TShowProgressThread.Execute;
begin
DoSomething;
DoExecute;
DoSomething
end;
и в потомках уже перекрывался DoExecute... Поэтому execute мне недоступен.
Aleksandr (2002-07-09 13:25:00) [8]Оппа... SomeThread, соответственно - потомок, коли Execute у всех перекрывается? А почему так? И еще вопрос, если можно - в программе есть список - потомок TList, потокам не принадлежащий, который создает эти самые TADOQuery для потоков по их вызовам. В нем Coinitialize не нужна?
Digitman (2002-07-09 13:21:00) [9]вот это
procedure TSomeThread.Execute;
begin
Coinitialize(nil);
try
finally
Couninitialize;
end;
end;
верно.
Все остальное (что ты привел) - нет.
Aleksandr (2002-07-09 13:14:00) [10]Так, не понял, что неверно. При создании - да, в теле констрактора. То есть у базового потока:
constructor TShowProgressThread.Create;
begin
Inherited Create(true);
Coinitialize(nil);
DoSomething
end;
destructor TShowProgressThread.Destroy;
begin
DoSomething;
Couninitialize;
Inherited
end;
у потомков:
constructor TQueryThread.Create;
begin
Inherited Create;
FQuery:=TblList.GetADOQuery;
DoSomething
end;
Digitman (2002-07-09 13:05:00) [11]"при создании" - надо понимать "в теле конструктора" ?
Этио неверно. Конструктор вызвается другим потоком, а не тем, что собственно создается и в котором планируется обращение к OLE/COM