-
Добрый день !
Реализуется OPC-сервер на Delphi. В виде приложения прекрасно работает. Тестируем Матриконом. При переносе в сервис начинаются проблемы.
Если сервис не запущен в момент установки соединения, то соединение, понятно, не устанавливается. Если запустить сервис, то при установке соединения запускается еще один экземпляр приложения (какого черта !!! - понятное дело, без настроек и всего остального, что крутится в старом экземпляре), работает несколько секунд и вылетает с ошибкой 0x800706BA (Сервер RPC недоступен). Это при том, что идут всего навсего вызовы GetState, завершающиеся успешно.
-
> то при установке соединения запускается еще один экземпляр > приложения (какого черта !!!
у вас сервер в ехе и при создании сервера выставили Instancing в Multiple Instance . Или вообще ничего не выставляли, там это стоит по умолчанию.
-
Да уж, давненько я с сервисами не баловался. Но при этом в виде приложения эта штука будучи запущенной повторно не запускается. Что касается Instancing, то действительно стоит в ciMultiInstance, но эффект не меняется и при ciSingleInstance.
Сейчас игрался - вынес создание всех фактори в OnServiceStart - вообще коннектиться перестало...
-
Может все-таки так надо
2.2. OPC-сервер
Для каждого OPC-клиента, OPC-сервер формирует объект типа OPC-сервер и создает специальный (безраздельный) коммуникационный канал (thread). Это защищает обмен данными от влияния других OPC-клиентов и повышает производительность OPC-сервера.
-
Тут threads ни при чем - создается не thread, а именно запускается новый экземпляр exe. А надо чтобы создавался именно thread.
И продолжает оставаться открытым вопрос с вылетанием процесса в считанные секунды.
-
> Relentless © (14.08.07 17:27) [4]
Показывай код обработки событий сервиса - OnCreate, OnDestroy, OnStart, OnStop, OnExecute ..
-
-
Спасибо за ссылку, но вроде бы не похоже на мой случай.
Итак, код...
OnServiceStart: Debug('Registering OPC instance...'); CoInitialize(nil); RegisterTheServer('MYOPC.DA.1'); // Типовая конструкция, пишушая в реестр Debug('Starting service...'); ReadConfiguration; // Читаем конфиг и запускаем коллекторы // данных Debug('Service start completed !');
OnServiceStop: Debug('Stopping service...'); StopServerCommunications; // Останавливаем коллекторы данных и // прибиваем живые соединения OPC CoUninitialize; Debug('Shutdown completed.');
В Debug используются переменные, описанные в var-секции модуля: var LogFileSize: Integer = 0; LogFileStarted: Boolean = False; LogToFile: String = '';
Внутри Debug если LogFileStarted не установлен, log-файл пуржится.
Собственно код, где создаются COM-объекты (расположен в initialization своих модулей): TAutoObjectFactory.Create(ComServer, TDA2, Class_DA2, ciMultiInstance, tmApartment); ComServer.UIInteractive := False;
-
-
-
Спасибо за ссылку. Видимо это то, что нужно, но у меня уже возникает желание автора COM повесить за одно место.
-
> у меня уже возникает желание автора COM повесить за одно > место
Это почему же ?)
-
-
Прямо чертовщина какая-то. Код регистрации 100% одинаковый - я передрал один в один из примера. Разве что guid-ы поменялись. Пример работает, мой код ругается на ошибку регистрации....
Причем один раз он как-то умудрился регистрацию проскочить, но я поздно заметил.
-
Кое-как удалось залатать, исключив ROTFLAGS_ALLOWANYCLIENT.
Теперь OPC-клиент вообще не хочет коннектиться - говорит что служба не зарегистрирована.
-
> Relentless
Свяжись с автором примера Набережных С. (с), я думаю он даст тебе толковую подсказку.
-
|