Форум: "WinAPI";
Текущий архив: 2004.02.06;
Скачать: [xml.tar.bz2];
ВнизСоздание сервиса используя TService Найти похожие ветки
← →
Dimmu (2003-12-01 14:28) [0]Здравствуйте. Кто нить может привести код готового сервиса на основе класса TService? Спасибо.
← →
Digitman (2003-12-01 14:57) [1]
> код готового сервиса
который делает ЧТО ????
← →
Dimmu (2003-12-01 15:00) [2]Нет, что он делает мне не важно, пускай в том месте будет что то то типа
repeat
// код который крутится
until Terminated;
Самое важное реакции на всякие остановки и т.п. Я пытался запустить пример из хелпа, но что то не получилось.
← →
Digitman (2003-12-01 15:24) [3]
> что то не получилось
ЧТО не получилось ?
нормальный старт - возврат Started = True в обработчике OnStart()
нормальный останов - возврат Stopped = True в обработчике OnStop()
куда уж проще ..
← →
zapped (2003-12-02 02:28) [4]2Dimmu (01.12.03 15:00) [2]
присоединяюсь к Digitman: ЧТО не получилось?
← →
Dimmu (2003-12-02 10:51) [5]Привожу код, чтоб все стало ясно и что вылазиит при старта сервиса.
unit UMain;
interface
uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, SvcMgr, Dialogs;
type
TSparkyThread = class(TThread)
public
procedure Execute; override;
end;
TService1 = class(TService)
procedure ServiceExecute(Sender: TService);
private
public
function GetServiceController: TServiceController; override;
procedure ServiceStart(Sender: TService; var Started: Boolean);
procedure ServicePause(Sender : TService; var Paused : Boolean);
Procedure ServiceContinue(Sender: TService;
var Continued: Boolean);
procedure ServiceStop(Sender: TService; var Stopped: Boolean);
end;
var
Service1: TService1;
SparkyThread: TSparkyThread;
implementation
{$R *.DFM}
procedure TSparkyThread.Execute;
begin
while not Terminated do
begin
MessageBox(0,"asd","qwe",0);
Sleep(5000);
end;
end;
procedure ServiceController(CtrlCode: DWord); stdcall;
begin
Service1.Controller(CtrlCode);
end;
function TService1.GetServiceController: TServiceController;
begin
Result := ServiceController;
end;
procedure TService1.ServiceStart(Sender: TService; var Started: Boolean);
begin
SparkyThread:=TSparkyThread.Create(false);
Started := True;
end;
procedure TService1.ServicePause(Sender: TService; var Paused: Boolean);
begin
SparkyThread.Suspend;
Paused := True;
end;
procedure TService1.ServiceStop(Sender: TService; var Stopped: Boolean);
begin
SparkyThread.Terminate;
Stopped:=true;
end;
procedure TService1.ServiceContinue(Sender: TService;
var Continued: Boolean);
begin
SparkyThread.Resume;
Continued:=true;
end;
procedure TService1.ServiceExecute(Sender: TService);
begin
while not Terminated do begin
ServiceThread.ProcessRequests(True);
end;
end;
end.
Вроде все просто, но при запуске появляется след. ошибка:
Exception EReadError in module (не важно) at (тут адрес)
Error reading Service1.OnPause: Invalid property value.
Что в OnPause не так не могу догнать.
← →
zapped (2003-12-02 11:50) [6]щас сделал всё по твоему коду :)))
не работает ;)))
обработчики, видать САМ приписывал, а не через Object Inspector :))
перенеси описание их из секции public туда, где они по умолчанию пишутся Object Inspector`ом :))
всё заработает... как я до этого додумался, сам не знаю :)))
TService1 = class(TService)
procedure ServiceExecute(Sender: TService);
procedure ServiceStart(Sender: TService; var Started: Boolean);
procedure ServicePause(Sender : TService; var Paused : Boolean);
Procedure ServiceContinue(Sender: TService;
var Continued: Boolean);
procedure ServiceStop(Sender: TService; var Stopped: Boolean);
public
function GetServiceController: TServiceController; override;
end;
← →
Dimmu (2003-12-02 12:14) [7]
> to zapped
Перенес все как ты сказал, теперь служба долго запускается и в итоге пишет, что служба вовремя не ответила на запрос и по сему не запущена. Так ведь Started:=true я думаю как раз за это и отвечает. Не догоняю от чего так. И еще, если не в лом, скажи как происходит связывание моего потока (TSparkyThread) и ServiceThread. То есть что делает вот эта строка: ServiceThread.ProcessRequests(True); ?
← →
Digitman (2003-12-02 13:45) [8]для начала объясни, на кой шут тебе еще один поток, TSparkyThread ? чем это обосновано ?
код сервиса и так исполняется в отдельном потоке
← →
Dimmu (2003-12-02 14:10) [9]
>to: Digitman
Сделал как в хелпе. Если не нужен, то как должен выглядеть ServiceExecute? Что типа:
procedure TService1.ServiceExecute(Sender: TService);
begin
while not Terminated do begin
MessageBox(0,"asd","qwe",0);
Sleep(5000);
ServiceThread.ProcessRequests(True);
end;
end;
Или как то по другому?
← →
Digitman (2003-12-02 14:14) [10]
> что делает вот эта строка: ServiceThread.ProcessRequests(True);
>
эта строка отвечает за прием/диспетчеризацию/обработку сообщений-контролов, посылаемых сервис-менеджером потоку сервиса, т.е. Start, Stop, Pause, Continue, Shutdown и пр.пользовательские
без циклического выдова этого метода сервис не будет реагировать на команды сервис-менеджера
если событие сервиса OnExecute() не обрабатывается тобой, то вызов этого метода происходит неявно в коде модуля SvsMgr, в противном случае ответственность за своевременный вызов этого метода возлагается на тебя как на прикл.программиста
procedure TServiceThread.Execute;
var
msg: TMsg;
Started: Boolean;
begin
PeekMessage(msg, 0, WM_USER, WM_USER, PM_NOREMOVE); { Create message queue }
try
FService.Status := csStartPending;
Started := True;
if Assigned(FService.OnStart) then FService.OnStart(FService, Started);
if not Started then Exit;
try
FService.Status := csRunning;
if Assigned(FService.OnExecute) then
FService.OnExecute(FService)
else
ProcessRequests(True);
ProcessRequests(False);
except
on E: Exception do
FService.LogMessage(Format(SServiceFailed,[SExecute, E.Message]));
end;
except
on E: Exception do
FService.LogMessage(Format(SServiceFailed,[SStart, E.Message]));
end;
end;
← →
Digitman (2003-12-02 14:19) [11]
> Сделал как в хелпе. Если не нужен, то как должен выглядеть
> ServiceExecute?
я речь веду о смысле, заложенном тобой в использовании TSparkyThread, а не о TServiceThread ... он тебе ЗАЧЕМ ?
← →
Digitman (2003-12-02 14:25) [12]в общем случае я как правило поступаю так :
procedure TService1.ProcessSpecialMessage(var Msg: TMessage);
begin
try
... обработка сообщения WM_SOMEMESSAGE, по возможности - максимально короткая по времени
except
end;
end;
procedure TService1.ServiceExecute(Sender: TService);
var
Msg: TMsg;
begin
while not Terminated do
begin
WaitMessage;
if PeekMessage(Msg, 0, WM_SOMEMESSAGE, WM_SOMEMESSAGE, PM_REMOVE) then
ProcessSpecialMessage(PMessage(@Msg.Message)^)
else
ServiceThread.ProcessRequests(False);
end;
end;
в рез-те сервис получает способность быстро реагировать как на контролы, посылаемые системным сервис-менеджером, так и на пользовательские сообщения, посылаемые треду сервиса вызовами PostThreadMessage(WM_SOMEMESSAGE)
Страницы: 1 вся ветка
Форум: "WinAPI";
Текущий архив: 2004.02.06;
Скачать: [xml.tar.bz2];
Память: 0.48 MB
Время: 0.053 c