Written on: 13. 10. 2015 [13:58]
|
zeronineseven
Владимир Лебедев
Topic creator
registered since: 07.10.2015
Posts: 6
|
Здравствуйте!
Разрабатываю собственный DAQ-модуль на основе шаблона "src/moduls/daq/=Tmpl=" под OpenSCADA 0.9(svn ревизия 2298) на Debian с ядром 3.16.0-4-amd64 и компилятором g++ 4.9.2-10.
Необходимо, чтобы при создании контроллера автоматически создавался также и некоторый параметр, а внутри параметра, в свою очередь, некоторый атрибут. С первым никаких проблем не возникло(создаю параметр в TController::postEnable), а вот нормально сделать создание атрибутов пока не получается. Т.к. предполагается, что типов параметров должно быть несколько, то я решил использовать TTypeParam и, поглядывая на штатные DAQ-модули(SMH2Gi), сделал добавление атрибута в TTypeParam::enable (prm->elem().fldAdd(new TFld("Test", _("Test"), TFld::Integer, TFld::NoWrite));) - всё заработало, но создаются атрибуты только при первом старте параметра, а не при его создании (что логично). Исходя из того, что TTypeParam имеет callback-метод create, я попытался перенести создание атрибута туда, но это приводит либо к segfault(если запускать с уже настроенным oscada.xml), либо к зависанию всей скады(подозреваю, что возникает какой-то deadlock). По этому поводу несколько вопросов:
Это какое-то предумышленное ограничение или баг в OpenSCADA 0.9(я пробовал на нескольких более ранних ревизиях текущей рабочей версии - тоже самое)?
По тому ли пути я иду, чтобы решить поставленную задачу? Или этого можно добиться как-то проще/правильнее?
Заранее благодарю за любую помощь!
|
Written on: 14. 10. 2015 [10:08]
|
roman
Roman Savochenko
Moderator Contributor Developer
registered since: 12.12.2007
Posts: 3750
|
"zeronineseven" wrote:
Необходимо, чтобы при создании контроллера автоматически создавался также и некоторый параметр, а внутри параметра, в свою очередь, некоторый атрибут.
В целом это нехорошо, хотя есть, например, в DAQ.System. Причём не в момент создания объекта контроллера, а при установке флага "Автоматический поиск активных источников данных и создание параметров для них" и включения объекта контроллера. Т.е., в целом недопустимо создание объектов параметров в момент создания объекта контроллера. При включени можно.
"zeronineseven" wrote:
С первым никаких проблем не возникло(создаю параметр в TController::postEnable), а вот нормально сделать создание атрибутов пока не получается. Т.к. предполагается, что типов параметров должно быть несколько, то я решил использовать TTypeParam и, поглядывая на штатные DAQ-модули(SMH2Gi), сделал добавление атрибута в TTypeParam::enable (prm->elem().fldAdd(new TFld("Test", _("Test"), TFld::Integer, TFld::NoWrite));) - всё заработало, но создаются атрибуты только при первом старте параметра, а не при его создании (что логично). Исходя из того, что TTypeParam имеет callback-метод create, я попытался перенести создание атрибута туда, но это приводит либо к segfault(если запускать с уже настроенным oscada.xml), либо к зависанию всей скады(подозреваю, что возникает какой-то deadlock). По этому поводу несколько вопросов:
Это какое-то предумышленное ограничение или баг в OpenSCADA 0.9(я пробовал на нескольких более ранних ревизиях текущей рабочей версии - тоже самое)?
Это непонимание. TTypeParam наследуется от статического набора структур атрибутов TElem, изменение которых в принципе недопустимо, поскольку, как минимум, вызовет их редактирование для всех параметров этого типа. Для формирования дополнительных атрибутов необходимо, в том-же "create()" добавлять их в TElem экземпляра данного параметра, смотрим работающие и не падающие: DAQ.AMRDevs
"zeronineseven" wrote:
По тому ли пути я иду, чтобы решить поставленную задачу? Или этого можно добиться как-то проще/правильнее?
Если набор атрибутов статичен по типам параметров, то проще через разные TTypeParam. Если сильно динамичен, то один TTypeParam и создавать в отдельном контейнере атрибутов TElem каждого экземпляра параметра и исключительно в момент включения параметра, а не его создания. Именно для этого статус и режим "Включен" предусмотрен!
Learn, learn and learn better than work, work and work.
|
Written on: 05. 11. 2015 [13:43]
|
zeronineseven
Владимир Лебедев
Topic creator
registered since: 07.10.2015
Posts: 6
|
Спасибо за ответ, roman!
"roman" wrote:
Т.е., в целом недопустимо создание объектов параметров в момент создания объекта контроллера. При включени можно.
Не могли бы вы объяснить, почему так? Архитектурное ли это ограничение, или концептуальное?
"roman" wrote:
Для формирования дополнительных атрибутов необходимо, в том-же "create()" добавлять их в TElem экземпляра данного параметра, смотрим работающие и не падающие: DAQ.AMRDevs
Видимо я неудачно объяснил. Если я правильно понял, то сейчас у меня всё сделано именно так, как вы описали:
class TMdPrm : public OSCADA::TParamContr {
public:
...
//!!! Parameter's structure element link function
OSCADA::TElem &elem( ) { return p_el; }
private:
//!!! Post-enable processing virtual function
void TMdPrm::postEnable(int flag) {
TParamContr::postEnable(flag);
if(!vlElemPresent(&p_el)) {
vlElemAtt(&p_el);
}
}
OSCADA::TElem p_el; //Work atribute elements
...
}
class MovementParam: public OSCADA::TTypeParam {
...
void MovementParam::create(TParamContr *raw_prm) {
TMdPrm *prm = static_cast<TMdPrm *>(raw_prm);
prm->elem().fldAdd(new TFld("Test", _("Test value"), TFld::Integer, TVal::DirWrite));
}
...
}
Если перенести код из ::create в ::enable, то всё работает(как в DAQ.AMRDevs), но в таком виде оно вызывает полное зависание OpenSCADA. В чём может быть проблема?
|