Top.Mail.Ru
Мастера DELPHI, Delphi programming community Титульная страница Поиск, карта сайта Написать письмо 
| Новости | Поиск | FAQ | Статьи | Книги | Новости VCL |
| Форумы ЧАТ | Орешник | KOL и MCK |
Форумы -» Основная («Начинающим»)/ Базы / WinAPI / Компоненты / Сети / Media / Игры / Corba и COM / KOL / FreePascal / .Net / Прочее / RSDN.ORG

« предыдущая ветвь | форум | следующая ветвь »

Service & DLL


HelpMy ©   (2005-09-27 07:16:00) 

При попытке из Service подключения DLL и вызова из нее процедуры появляется ошибка. Процедура в DLL подключается к базе и делает запись. Тот же самый вызов из приложения работает без проблем. Неужели Service не может работать с библиотеками? Не хотелось из Service запускать процесс.


Digitman   (2005-09-27 12:15:00) [1]

+ сервисы имеют ВСТРОЕННЫЙ механизм (и его API) для протоколирования работы сервиса

см. LogMessage method (TService)


Digitman   (2005-09-27 12:13:00) [2]

см. топик "Debugging service applications"

+ используй для отлад.целей вставку оператора, осуществляющего задержку, достаточную по времени для того чтобы ты успел приаттачиться к процессу сервиса


Digitman   (2005-09-27 12:06:00) [3]

в станд.справке есть инф-ция о принципе отладки сервиса средствами встр.отладчика


> не успею


ну так поставь задержку, например, в обработчик OnStart !


HelpMy   (2005-09-27 11:41:00) [4]

To Digitman ©   (27.09.05 11:03) [14]

воспользуешься штатными средствами штатного же встроенного отладчика
Делфи

Проблема с отладкой DLL.
Подключить к процессу (сервису) я не успею, он при запуске сразу же обращается к DLL.
В меню RUN > Parameters... сервис будет запушен как exe.


Digitman   (2005-09-27 11:03:00) [5]


> AddToLog() присутствует и в сервисе и в библиотеке


и зачем такие выкрутасы ?

организуй в коде сервиса единуюпроцедуру протоколирования.

а еще лучше будет, если для отладки своего сервиса вместо сомнительных по надежности алгоритмов протоколирования ты воспользуешься штатными средствами штатного же встроенного отладчика Делфи


HelpMy   (2005-09-27 10:53:00) [6]

To Digitman ©   (27.09.05 10:06) [12]

AddToLog() присутствует и в сервисе и в библиотеке.
IsMultiThread := True нужно попробовать


Digitman   (2005-09-27 10:06:00) [7]

я что-то не понял ...

procedure TLabServ.ServiceExecute(Sender: TService);
begin
AddToLog('ServiceExecute');
try
..

откуда тут взялась AddToLog(), если она объявлена и реализована в библиотеке, которую ты еще НЕ загрузил на этот момент ?

или у тебя есть ЕЩЕ одна AddToLog(), к библиотеке отношения не имеющая


> exports RegistrInDB;  
> begin
> IsMultiThread := True;//важно , потому что сервис будет вызывать ф-ции библ-ки в доп.потоке !

while not Terminated do
  ServiceThread.ProcessRequests( True);  // пока у тебя сервис более ничем не занят (регистрация уже выполнена ранее по тексту), лучше всего будет крутиться в цикле с ожиданиемконтроллеров


HelpMy   (2005-09-27 09:53:00) [8]

Библиотека приняла вид:

library Shlproc;

uses
 SysUtils,
 Classes;

const Log = 'c:\log.txt';
var
 F:        TextFile;

procedure AddToLog(S: String);
begin
 AssignFile(F, Log);
 Append(F);
 Writeln(F, 'Shlproc  ' + TimeToStr(Time) + '  ' + S);
 CloseFile(F);
end;

procedure RegistrInDB(Flag: byte);
begin
 AddToLog('Попытка выполнения');
end;

exports RegistrInDB;  
begin

end.

Рестрироваться пытаюсь при запуске сервиса

procedure TLabServ.ServiceExecute(Sender: TService);
begin
 AddToLog('ServiceExecute');
 try
    RegisterPC(0);
   AddToLog('Регистрация 0');
 except
   on E: Exception do
   begin
     AddToLog(E.ClassName + '  ' + e.Message);
   end;
 end;
 while Runing do
 Sleep(10);
 ServiceThread.ProcessRequests(False);  {}
 AddToLog('ServiceExecute успешно');
end;

RegisterPC(0);приведен в

HelpMy   (27.09.05 08:39) [2]

То Digitman ©   (27.09.05 09:32) [10]
соглашения о вызове точно соблюдены ?

... можно уточнить?


Digitman   (2005-09-27 09:32:00) [9]

соглашения о вызове точно соблюдены ?


Leonid Troyanovsky   (2005-09-27 09:31:00) [10]


> HelpMy   (27.09.05 09:27) [7]

> Похоже, что проблема с адресами сервиса и библиотеки.


Пока таких проблем ты не демонстрировал.

--
Regards, LVT.


Leonid Troyanovsky   (2005-09-27 09:28:00) [11]


> HelpMy   (27.09.05 09:10) [5]
> Перед
>
> TDM.Create(Application);
>
> добавил:
>
> AddToLog('Попытка выполнения');
>
> В Log запись не происходит!!!


Тогда сознавайся, что есть в initilization библиотечных модулей,
между begin..end. оной и т.д.

--
Regards, LVT.


HelpMy   (2005-09-27 09:27:00) [12]

Оставил в процедуре единственную строку записи в лог файл.

AddToLog('Попытка выполнения');

Результат тот же.
Приложение без проблем, сервис гонит все ту же ошибку.
Похоже, что проблема с адресами сервиса и библиотеки.


HelpMy   (2005-09-27 09:19:00) [13]

TO Digitman ©   (27.09.05 09:09) [4]
TDM.Create и TDM.OnCreate ни как не используются.
Это модуль данных, в который помещены компоненты
TIBDatabase, TIBSQL, TIBTransaction.

Ниже значимая часть dfm:

 object Query: TIBSQL
   Database = Base
   ParamCheck = True
   Transaction = Tr
   Left = 120
   Top = 16
 end
 object Tr: TIBTransaction
   Active = False
   DefaultDatabase = Base
 end
 object Base: TIBDatabase
   DatabaseName = 'localhost:test'
   Params.Strings = (
     'user_name=sysdba'
     'password=masterkey'
     'lc_ctype=WIN1251')
   LoginPrompt = False
   DefaultTransaction = Tr
   SQLDialect = 3
 end

Судя по HelpMy   (27.09.05 09:10) [5]
Ошибка происходит до создания DM.


HelpMy   (2005-09-27 09:10:00) [14]

Перед

TDM.Create(Application);

добавил:

AddToLog('Попытка выполнения');

В Log запись не происходит!!!


Digitman   (2005-09-27 09:09:00) [15]


> HelpMy   (27.09.05 08:39) [2]


что у тебя происходит в конструирующем методе TDM.Create и обработчике события TDM.OnCreate ?


Leonid Troyanovsky   (2005-09-27 08:52:00) [16]


> HelpMy   (27.09.05 08:39) [2]

> Эту же процедуру библиотеки вызываю из Приложения, вызов
> слово в слово как и в сервисе, все работает.


Твой сервис, очевидимо, не может TDM.Create(Application).
Такое может случиться, если у него, например,
нет прав на сетевые подключения (System, Local Service).

--
Regards, LVT.


HelpMy   (2005-09-27 08:39:00) [17]

Это вызов из сервиса:
procedure TLabServ.RegisterPC(Flag: byte);
type
 TLibProc = procedure(Flag: byte);
var
 LibHandle: THandle;
 LibProc: TLibProc;
const LibName  = 'Shlproc.dll';
     ProcName = 'RegistrInDB';
begin
 LibHandle := LoadLibrary(LibName);
 AddToLog('Регистрация');
 if LibHandle <> 0 then
 begin
   try
     try
       @LibProc := GetProcAddress(LibHandle, ProcName);
       AddToLog('Адрес процедуры ' + IntToStr(Integer(@LibProc)));
       if @LibProc <> nil
         then LibProc(Flag)
         else AddToLog('Не удалось найти функцию ' + ProcName);
     finally
       FreeLibrary(LibHandle);
     end;
   except
     on E: Exception do AddToLog(E.ClassName + '  ' + e.Message);
   end;
 end
 else AddToLog('Не удалось найти библиотеку ' + LibName);
end;

Это запись в Log, при вызове:
8:24:06  Регистрация
8:24:06  Адрес процедуры 17744456
8:24:07  EAccessViolation  Access violation at address 00403D42 in module 'Serv.exe'. Read of address 011355D0

Это сама процедура в библиотеке:
procedure RegistrInDB(Flag: byte);
begin
DM := TDM.Create(Application);
 try
   try
     DM.Base.Open;
     if not DM.Base.Connected then begin
                                     AddToLog('База недоступна');
                                     Exit;
                                   end
                              else AddToLog('Подключение успешно');
     DM.Query.SQL.Text := 'EXECUTE PROCEDURE REGISTER(:PC_NAME, :FLAG)';
     DM.Tr.StartTransaction;
     DM.Query.Params[0].AsString  := 'QWERTY';
     DM.Query.Params[1].AsInteger := 0;
     DM.Query.ExecQuery;
     DM.Tr.Commit
   except
     on E: Exception do
     begin
       AddToLog(E.ClassName + '  ' + e.Message);
       DM.Tr.Rollback;
       DM.Base.Close;
     end;
   end;
   finally
     DM.Free;
   end;
end;

Эту же процедуру библиотеки вызываю из Приложения, вызов слово в слово как и в сервисе, все работает.


Digitman   (2005-09-27 08:21:00) [18]


> появляется ошибка


какая ?


Наверх

Титульная страница Поиск, карта сайта Написать письмо