Я создал несколько сервисов в Delphi 7, и у меня не было этой проблемы. Теперь, когда я запустил новое сервисное приложение в XE2, оно не останавливается должным образом. Я не знаю, что я делаю неправильно, или это может быть ошибка в сервисах XE2.
Процедура выполнения выглядит так:
procedure TMySvc.ServiceExecute(Sender: TService);
begin
try
CoInitialize(nil);
Startup;
try
while not Terminated do begin
DoSomething; //Problem persists even when nothing's here
end;
finally
Cleanup;
CoUninitialize;
end;
except
on e: exception do begin
PostLog('EXCEPTION in Execute: '+e.Message);
end;
end;
end;
У меня никогда не было исключения, как видите, я регистрирую любое исключение. PostLog
сохраняется в файл INI, который отлично работает. Сейчас я использую компоненты ADO, поэтому использую CoInitialize()
и CoUninitialize
. Он подключается к БД и правильно выполняет свою работу. Проблема возникает только тогда, когда я останавливаю эту службу. Windows выдает мне следующее сообщение:
Потом служба продолжается. Я должен остановить это во второй раз. Во второй раз он останавливается, но со следующим сообщением:
Файл журнала показывает, что служба успешно освободилась (событие OnDestroy
было зарегистрировано), но никогда не останавливалась (OnStop
никогда не регистрировалась).
В приведенном выше коде у меня есть две процедуры Startup
и Cleanup
. Они просто создают / уничтожают и инициализируют / деинициализируют мои необходимые вещи ...
procedure TMySvc.Startup;
begin
FUpdateThread:= TMyUpdateThread.Create;
FUpdateThread.OnLog:= LogUpdate;
FUpdateThread.Resume;
end;
procedure TMySvc.Cleanup;
begin
FUpdateThread.Terminate;
end;
Как видите, у меня запущен вторичный поток. Эта служба фактически имеет множество потоков, работающих таким образом, и основной поток службы регистрирует только события из каждого потока. У каждого потока разные обязанности. Потоки сообщают правильно, и они также должным образом завершаются.
Что могло быть причиной этой остановки? Если мой опубликованный код ничего не раскрывает, я могу опубликовать дополнительный код позже - просто нужно его «преобразовать» из-за внутреннего именования и т. Д.
ИЗМЕНИТЬ
Я только что начал НОВЫЙ сервисный проект в Delphi XE2, и у меня такая же проблема. Это весь мой код ниже:
unit JDSvc;
interface
uses
Winapi.Windows, Winapi.Messages, System.SysUtils, System.Classes, JDSvcMgr;
type
TJDService = class(TService)
procedure ServiceExecute(Sender: TService);
private
FAfterInstall: TServiceEvent;
public
function GetServiceController: TServiceController; override;
end;
var
JDService: TJDService;
implementation
{$R *.DFM}
procedure ServiceController(CtrlCode: DWord); stdcall;
begin
JDService.Controller(CtrlCode);
end;
function TJDService.GetServiceController: TServiceController;
begin
Result := ServiceController;
end;
procedure TJDService.ServiceExecute(Sender: TService);
begin
while not Terminated do begin
end;
end;
end.
FUpdateThread.Free
, который вызовет WaitFor - person David Heffernan   schedule 13.02.2012FreeOnTerminate:= True;
- person Jerry Dodge   schedule 13.02.2012TThread.Free
, я вижу традиционныйTObject.Free
. Также добавитьWaitFor
не получилось, проблема осталась. - person Jerry Dodge   schedule 13.02.2012Destroy
. И да,WaitFor
называется. - person David Heffernan   schedule 13.02.2012FreeOnTerminate
, это может легко стать проблемой. Зачем ты это делаешь? Почему вы хотите это сделать. УстановитеFreeOnTerminate
на False и вызовитеFUpdateThread.Free
изCleanup
. Нет смысла звонитьTerminate
, поскольку это будет сделано за вас, когда вы позвонитеFree
. - person David Heffernan   schedule 13.02.2012while not Terminated do begin .. end;
вOnExecute
обработчик событий. См. Добавленный код выше. - person Jerry Dodge   schedule 13.02.2012ServiceThread.ProcessRequests(False);
). Так это что-то новое со времен D7 или что-то, что было там, но не всплывало до сих пор? - person Jerry Dodge   schedule 13.02.2012ProcessRequests
, когда я писал свой ответ. Я пришел к такому же выводу независимо. Однако я удалил свой ответ, поскольку вы явно опередили меня. - person David Heffernan   schedule 13.02.2012