Commit 90f84c13 authored by Vitaly Lipatov's avatar Vitaly Lipatov Committed by Pavel Vainerman

fix spell errors (via aspell based script)

parent 9f61b75d
...@@ -88,7 +88,7 @@ interface IOController_i : UniSetManager_i ...@@ -88,7 +88,7 @@ interface IOController_i : UniSetManager_i
void calibrate( in uniset::ObjectId sid, in CalibrateInfo ci, in uniset::ObjectId adminId ) raises(NameNotFound); void calibrate( in uniset::ObjectId sid, in CalibrateInfo ci, in uniset::ObjectId adminId ) raises(NameNotFound);
CalibrateInfo getCalibrateInfo( in uniset::ObjectId sid ) raises(NameNotFound); CalibrateInfo getCalibrateInfo( in uniset::ObjectId sid ) raises(NameNotFound);
// --- Интерфес получения информации о всех датчиках --- // --- Интерфейс получения информации о всех датчиках ---
/*! Информация датчике */ /*! Информация датчике */
struct SensorIOInfo struct SensorIOInfo
{ {
...@@ -139,7 +139,7 @@ interface IOController_i : UniSetManager_i ...@@ -139,7 +139,7 @@ interface IOController_i : UniSetManager_i
{ {
long value; long value;
// могут быть проблеммы в 64bit-ных // могут быть проблемы в 64bit-ных
unsigned long tv_sec; /*!< время последнего изменения датчика, секунды (clock_gettime(CLOCK_REALTIME) */ unsigned long tv_sec; /*!< время последнего изменения датчика, секунды (clock_gettime(CLOCK_REALTIME) */
unsigned long tv_nsec; /*!< время последнего изменения датчика, nanosec (clock_gettime(CLOCK_REALTIME) */ unsigned long tv_nsec; /*!< время последнего изменения датчика, nanosec (clock_gettime(CLOCK_REALTIME) */
uniset::ObjectId supplier; /*!< идентификатор того, кто менял датчик (последний раз) */ uniset::ObjectId supplier; /*!< идентификатор того, кто менял датчик (последний раз) */
...@@ -178,7 +178,7 @@ interface IONotifyController_i : IOController_i ...@@ -178,7 +178,7 @@ interface IONotifyController_i : IOController_i
{ {
}; };
/*! Универсальная функция заказа уведомления об изменнии датчика. /*! Универсальная функция заказа уведомления об изменении датчика.
* \sa UniversalIO::UniversalIOController::askSensor() * \sa UniversalIO::UniversalIOController::askSensor()
*/ */
void askSensor(in uniset::ObjectId sid, in uniset::ConsumerInfo ci, in UniversalIO::UIOCommand cmd ) raises(NameNotFound,IOBadParam); void askSensor(in uniset::ObjectId sid, in uniset::ConsumerInfo ci, in UniversalIO::UIOCommand cmd ) raises(NameNotFound,IOBadParam);
...@@ -205,7 +205,7 @@ interface IONotifyController_i : IOController_i ...@@ -205,7 +205,7 @@ interface IONotifyController_i : IOController_i
{ {
uniset::ThresholdId id; uniset::ThresholdId id;
long hilimit; /*!< верхняя граница срабатывания */ long hilimit; /*!< верхняя граница срабатывания */
long lowlimit; /*!< нижняя гранийа срабатывания */ long lowlimit; /*!< нижняя граница срабатывания */
ThresholdState state; ThresholdState state;
unsigned long tv_sec; /*!< время последнего изменения датчика, секунды (clock_gettime(CLOCK_REALTIME) */ unsigned long tv_sec; /*!< время последнего изменения датчика, секунды (clock_gettime(CLOCK_REALTIME) */
unsigned long tv_nsec; /*!< время последнего изменения датчика, nanosec (clock_gettime(CLOCK_REALTIME) */ unsigned long tv_nsec; /*!< время последнего изменения датчика, nanosec (clock_gettime(CLOCK_REALTIME) */
...@@ -217,7 +217,7 @@ interface IONotifyController_i : IOController_i ...@@ -217,7 +217,7 @@ interface IONotifyController_i : IOController_i
/*! Заказ порогового датчика /*! Заказ порогового датчика
* \sa UniversalIO::UniversalIOController::askThreshold() * \sa UniversalIO::UniversalIOController::askThreshold()
* \param tid - идентификатор порога * \param tid - идентификатор порога
* \param lowLimit - нижний порог срабатыания * \param lowLimit - нижний порог срабатывания
* \param hiLimit - верхний порог срабатывания * \param hiLimit - верхний порог срабатывания
* \param invert - инвертировать логику срабатывания * \param invert - инвертировать логику срабатывания
* Если invert=false, порог срабатывает при условии >= hilimit и отпускается при <= lowlimit * Если invert=false, порог срабатывает при условии >= hilimit и отпускается при <= lowlimit
...@@ -243,7 +243,7 @@ interface IONotifyController_i : IOController_i ...@@ -243,7 +243,7 @@ interface IONotifyController_i : IOController_i
typedef sequence<ThresholdList> ThresholdsListSeq; typedef sequence<ThresholdList> ThresholdsListSeq;
/*! получить список порогов для датчка "si" */ /*! получить список порогов для датчика "si" */
ThresholdList getThresholds( in uniset::ObjectId sid ) raises(NameNotFound); ThresholdList getThresholds( in uniset::ObjectId sid ) raises(NameNotFound);
/*! получить список ВСЕХ датчиков по которым созданы пороги */ /*! получить список ВСЕХ датчиков по которым созданы пороги */
......
...@@ -28,7 +28,7 @@ ...@@ -28,7 +28,7 @@
//{ //{
/*! /*!
* \interface UniSetObject_i * \interface UniSetObject_i
* \brief Базовый интерфес для всех объектов * \brief Базовый интерфейс для всех объектов
* \author Pavel Vainerman * \author Pavel Vainerman
* *
* Первичный базовый класс. Прародитель всех объектов в системе. * Первичный базовый класс. Прародитель всех объектов в системе.
......
...@@ -74,7 +74,7 @@ ...@@ -74,7 +74,7 @@
struct ConsumerInfo struct ConsumerInfo
{ {
ObjectId id; /*!< идентификатор заказчика */ ObjectId id; /*!< идентификатор заказчика */
ObjectId node; /*!< узел на котором он находится */ ObjectId node; /*!< узел, на котором он находится */
}; };
......
- сделать, чтобы можно было Debug пускать через syslog (да ещё и на другую машину) - сделать, чтобы можно было Debug пускать через syslog (да ещё и на другую машину)
- (IONotifyController): Разработать механизм заказа переодических уведомлений (msec), независимо от того, менялись ли датчики.. - (IONotifyController): Разработать механизм заказа периодических уведомлений (msec), независимо от того, менялись ли датчики..
- (IONotifyController): Разработать механизм заказа группы датчиков сразу (и ответ тоже группой) - (IONotifyController): Разработать механизм заказа группы датчиков сразу (и ответ тоже группой)
- циклическое хранилище для аварийных следов на основе SQLite - циклическое хранилище для аварийных следов на основе SQLite
......
...@@ -340,7 +340,7 @@ ...@@ -340,7 +340,7 @@
int askPause; /*!&lt; пауза между неудачными попытками заказать датчики */ int askPause; /*!&lt; пауза между неудачными попытками заказать датчики */
IOController_i::SensorInfo si; IOController_i::SensorInfo si;
bool forceOut; /*!&lt; флаг принудительного обноления "выходов" */ bool forceOut; /*!&lt; флаг принудительного обнуления "выходов" */
std::shared_ptr&lt;uniset::LogAgregator&gt; loga; std::shared_ptr&lt;uniset::LogAgregator&gt; loga;
std::shared_ptr&lt;DebugStream&gt; mylog; std::shared_ptr&lt;DebugStream&gt; mylog;
......
/*! \page page_Concept Основные понятия /*! \page page_Concept Основные понятия
В библиотеке \b uniset имеется ряд основопологающих кубиков (терминов), В библиотеке \b uniset имеется ряд основополагающих кубиков (терминов),
из которых складывается библиотека, и которые используются во многих из которых складывается библиотека, и которые используются во многих
местах данной документации. Здесь приводятся определения этих терминов. местах данной документации. Здесь приводятся определения этих терминов.
...@@ -29,7 +29,7 @@ ...@@ -29,7 +29,7 @@
но обладают уникальным идентификатором. но обладают уникальным идентификатором.
\section sec_Concept_Message Сообщения \section sec_Concept_Message Сообщения
Вся система взаимодейтсвия между объектами в основном Вся система взаимодействия между объектами в основном
построена на использовании сообщений (передаваемых построена на использовании сообщений (передаваемых
путём удаленного вызова специальных функций, путём удаленного вызова специальных функций,
посредством CORBA). При этом основные посредством CORBA). При этом основные
...@@ -39,7 +39,7 @@ ...@@ -39,7 +39,7 @@
Для разработчиков систем на основе libuniset, заложена Для разработчиков систем на основе libuniset, заложена
возможность определять свои типы сообщений, при этом их возможность определять свои типы сообщений, при этом их
идентификаторы \b должны начинатся от значения идентификаторы \b должны начинаться от значения
UniSetTypes::Message::TheLastFieldOfTypeOfMessage. UniSetTypes::Message::TheLastFieldOfTypeOfMessage.
\code \code
enum MyMessageTypes enum MyMessageTypes
...@@ -108,10 +108,10 @@ UniSetTypes::Message::TheLastFieldOfTypeOfMessage. ...@@ -108,10 +108,10 @@ UniSetTypes::Message::TheLastFieldOfTypeOfMessage.
будет присвоен идентификатор (просто по порядку). См. \ref UniSetTypes::ObjectIndex_XML будет присвоен идентификатор (просто по порядку). См. \ref UniSetTypes::ObjectIndex_XML
\note Следует иметь ввиду, что автоматическое присвоение идентификаторов, \note Следует иметь ввиду, что автоматическое присвоение идентификаторов,
\b зависит \b от \b положения описания объекта в конфигурацинном файле. \b зависит \b от \b положения описания объекта в конфигурационном файле.
Поэтому если вставить новый объект в любой секции, то все идентификаторы после него, Поэтому если вставить новый объект в любой секции, то все идентификаторы после него,
станут недействительными (сместятся на единицу). Т.е. необходимо отслеживать, станут недействительными (сместятся на единицу). Т.е. необходимо отслеживать,
что конфигурационные файлы на всех узлах собвпадают между собой. что конфигурационные файлы на всех узлах совпадают между собой.
\note Из-за не надёжности это способ не рекомендуется к использованию. \note Из-за не надёжности это способ не рекомендуется к использованию.
...@@ -161,7 +161,7 @@ UniSetTypes::Message::TheLastFieldOfTypeOfMessage. ...@@ -161,7 +161,7 @@ UniSetTypes::Message::TheLastFieldOfTypeOfMessage.
</Configurations> </Configurations>
\endcode \endcode
\note При этом за уникальностью(отсутсвием дублей) идентификаторов должен \note При этом за уникальностью(отсутствием дублей) идентификаторов должен
следить сам разработчик (хотя эта проверка может быть автоматизирована следить сам разработчик (хотя эта проверка может быть автоматизирована
не сложными скриптами). не сложными скриптами).
...@@ -187,7 +187,7 @@ UniSetTypes::Message::TheLastFieldOfTypeOfMessage. ...@@ -187,7 +187,7 @@ UniSetTypes::Message::TheLastFieldOfTypeOfMessage.
сообщения свой "датчик" и в случае необходимости послать сообщение сообщения свой "датчик" и в случае необходимости послать сообщение
выставлять его в "1". выставлять его в "1".
Удобство и универсальность датчиков (цифр) позволяет использовать для Удобство и универсальность датчиков (цифр) позволяет использовать для
передачи данных большое число различных протоколов, расчитанных передачи данных большое число различных протоколов, рассчитанных
на передачу цифровой информации (не текстовой). на передачу цифровой информации (не текстовой).
Например CAN, ModbusRTU, ModbusTCP и т.п. Например CAN, ModbusRTU, ModbusTCP и т.п.
......
...@@ -5,8 +5,8 @@ ...@@ -5,8 +5,8 @@
\section ConfigurationPage_secCommon Общее описание \section ConfigurationPage_secCommon Общее описание
Для конфигурирования сиситемы используется файл (обычно "configure.xml"). Для конфигурирования системы используется файл (обычно "configure.xml").
Конфигурация является глобальным объектом. Для получения доступа к ней используется фунуция auto conf = uniset_conf(); Конфигурация является глобальным объектом. Для получения доступа к ней используется функция auto conf = uniset_conf();
До начала работы, обычно в функции main(), конфигурация должна быть инициализирована при помощи функции uniset_init(). До начала работы, обычно в функции main(), конфигурация должна быть инициализирована при помощи функции uniset_init().
При этом третий параметр, указывающий название конфигурационного файла, является не обязательным. При этом третий параметр, указывающий название конфигурационного файла, является не обязательным.
По умолчанию обрабатывается аргумент командной строки --confile filename. По умолчанию обрабатывается аргумент командной строки --confile filename.
...@@ -42,7 +42,7 @@ int main(int argc, char **argv) ...@@ -42,7 +42,7 @@ int main(int argc, char **argv)
Для возможности задать напрямую параметры для omniORB заложена специальная секция <omniORB>. Для возможности задать напрямую параметры для omniORB заложена специальная секция <omniORB>.
В данную секцию можно записывать любые параметры поддерживаемые библиотекой omniORB. В данную секцию можно записывать любые параметры поддерживаемые библиотекой omniORB.
Формат и назавание параметров см. документацию по omniORB. Формат и название параметров см. документацию по omniORB.
Пример: Пример:
\code \code
......
...@@ -38,11 +38,11 @@ interface TestActiveProcess_i: UniSetObject_i ...@@ -38,11 +38,11 @@ interface TestActiveProcess_i: UniSetObject_i
На основе этих файлов вы реализуете свой интерфейс на С++. На основе этих файлов вы реализуете свой интерфейс на С++.
\section pgCP_secImplementation Реализация интерфейса на C++ \section pgCP_secImplementation Реализация интерфейса на C++
Необходимо создать класс реализующий объявленный интерфейс. Формирование названия класса и правила наследования Необходимо создать класс реализующий объявленый интерфейс. Формирование названия класса и правила наследования
см. \ref UniSetLibStylePage. см. \ref UniSetLibStylePage.
\par \par
Базовые функции интерфейса UniSetObject_i уже реализованы в классе UniSetObject. Поэтому остается только Базовые функции интерфейса UniSetObject_i уже реализованы в классе UniSetObject. Поэтому остается только
наследоваться от него и реализавать недостающие функции. В итоге получаем наследоваться от него и реализовать недостающие функции. В итоге получаем
\code \code
#ifndef TestActiveProcess_H_ #ifndef TestActiveProcess_H_
#define TestActiveProcess_H_ #define TestActiveProcess_H_
...@@ -62,7 +62,7 @@ interface TestActiveProcess_i: UniSetObject_i ...@@ -62,7 +62,7 @@ interface TestActiveProcess_i: UniSetObject_i
virtual ~TestActiveProcess(); virtual ~TestActiveProcess();
// ------- функции объевленные в IDL(интерфейс данного объекта) --------- // ------- функции объявленые в IDL(интерфейс данного объекта) ---------
virtual void on(); virtual void on();
virtual void off(); virtual void off();
...@@ -236,7 +236,7 @@ interface TestActiveProcess_i: UniSetObject_i ...@@ -236,7 +236,7 @@ interface TestActiveProcess_i: UniSetObject_i
\section pgCP_secLT_Object Создание автономного объекта, не зависящего от TimerService-а \section pgCP_secLT_Object Создание автономного объекта, не зависящего от TimerService-а
Для повышения автономности работы, можно создать процесс, который сам будет реализовывать таймеры. Для повышения автономности работы, можно создать процесс, который сам будет реализовывать таймеры.
Для этого достаточно при создании своего процесса наследоватся не от UniSetObject, а от UniSetObject_LT. Для этого достаточно при создании своего процесса наследоваться не от UniSetObject, а от UniSetObject_LT.
Т.е. код будет выглядеть так: Т.е. код будет выглядеть так:
\code \code
... ...
......
...@@ -24,7 +24,7 @@ ...@@ -24,7 +24,7 @@
- \b AO - аналоговый выход - \b AO - аналоговый выход
\section pgIOC_secAskFile Конфигурацонные ask-файлы \section pgIOC_secAskFile Конфигурационные ask-файлы
Формат файла имеет следующий вид: Формат файла имеет следующий вид:
\code \code
<IOConf readonly="1" dumptime="Wed Mar 23 14:14:42 2005"> <IOConf readonly="1" dumptime="Wed Mar 23 14:14:42 2005">
...@@ -98,7 +98,7 @@ ...@@ -98,7 +98,7 @@
- \a node - название узла. Если не задано, то считается Localhost. - \a node - название узла. Если не задано, то считается Localhost.
- \a iotype - Тип входа/выхода.( см. \ref pgIOC_secIOTypes ) - \a iotype - Тип входа/выхода.( см. \ref pgIOC_secIOTypes )
Следующие поля необзатяельны: Следующие поля необязательны:
- \a default - [1|0] значение по умолчанию. Т.е. значение на момент начального запуска. - \a default - [1|0] значение по умолчанию. Т.е. значение на момент начального запуска.
По умолчанию имеет значение "0". По умолчанию имеет значение "0".
- \a priority - Приоритет посылаемого уведомления (UniSetTypes::SensorMessage) об изменении - \a priority - Приоритет посылаемого уведомления (UniSetTypes::SensorMessage) об изменении
...@@ -125,7 +125,7 @@ ...@@ -125,7 +125,7 @@
- \a rmin - Минимальное "cырое" значение. ("сырое" - т.е. непосредственно получаемое) - \a rmin - Минимальное "cырое" значение. ("сырое" - т.е. непосредственно получаемое)
- \a rmax - Максимальное "сырое" значение - \a rmax - Максимальное "сырое" значение
Следующие поля необзатяельны: Следующие поля необязательны:
- \a default - значение по умолчанию. Т.е. значение на момент начального запуска. - \a default - значение по умолчанию. Т.е. значение на момент начального запуска.
По умолчанию имеет значение "0". По умолчанию имеет значение "0".
- \a priority - Приоритет посылаемого уведомления (UniSetTypes::SensorMessage) об изменении - \a priority - Приоритет посылаемого уведомления (UniSetTypes::SensorMessage) об изменении
...@@ -161,14 +161,14 @@ ...@@ -161,14 +161,14 @@
TRUE - при значении больше верхнего порога TRUE - при значении больше верхнего порога
FALSE - при значении меньше нижнего порога FALSE - при значении меньше нижнего порога
- \a id - идентификатор порога(число). Значение которое используется для передачи - \a id - идентификатор порога(число). Значение которое используется для передачи
в сообщении SensorMessage как идентифифкатор сработавшего порога. Должен в сообщении SensorMessage как идентификатор сработавшего порога. Должен
быть разный (уникальным) для разных порогов у одного аналогового датчика. быть разный (уникальным) для разных порогов у одного аналогового датчика.
В случае использования "sid" id указывать необязательно. В случае использования "sid" id указывать необязательно.
- \a inverse - [1|0] позволяет инвертировать логику для датчика, указанного в поле sid. - \a inverse - [1|0] позволяет инвертировать логику для датчика, указанного в поле sid.
В общем случае "пороги" не имеют отдельных уникальных идентификаторов. И каждый процесс В общем случае "пороги" не имеют отдельных уникальных идентификаторов. И каждый процесс
может заказать(сделать) себе любое количество "порогов" из одного аналогового датчика. может заказать(сделать) себе любое количество "порогов" из одного аналогового датчика.
Но существует возможность связать дискртеный датчик (в данном случае это будет фиктивный дискретный датчик) Но существует возможность связать дискретный датчик (в данном случае это будет фиктивный дискретный датчик)
с пороговым значением. Для этого прописывается следующая запись: с пороговым значением. Для этого прописывается следующая запись:
\code \code
<sensor name="MyProject/Sensors/AnalogSensor1_AS" node="" iotype="AI"> <sensor name="MyProject/Sensors/AnalogSensor1_AS" node="" iotype="AI">
...@@ -185,7 +185,7 @@ ...@@ -185,7 +185,7 @@
UniSetTypes::SensorMessage об изменении данного датчика. Заказывать уведомления UniSetTypes::SensorMessage об изменении данного датчика. Заказывать уведомления
можно об изменении не только "входов", но и "выходов". можно об изменении не только "входов", но и "выходов".
\section pgIOC_secSensorMessage Формат уведомления об изменнии состояния (значения) \section pgIOC_secSensorMessage Формат уведомления об изменении состояния (значения)
Для уведомления используется сообщение UniSetTypes::SensorMessage. Для уведомления используется сообщение UniSetTypes::SensorMessage.
- \a state - текущее значение для дискретного датчика - \a state - текущее значение для дискретного датчика
- \a value - текущее значения для аналогового датчика - \a value - текущее значения для аналогового датчика
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
- \ref pgIONC_secLT_Object - \ref pgIONC_secLT_Object
- \ref pgIONC_secRecomendation - \ref pgIONC_secRecomendation
Все i/o процессы должны наследоватся от класса IOController. Если вам необходимо написать i/o процесс, который Все i/o процессы должны наследоваться от класса IOController. Если вам необходимо написать i/o процесс, который
помимо операций i/o еще и уведомляет об изменении состояния входов(выходов), то наследуйтесь от класса IONotifyController. помимо операций i/o еще и уведомляет об изменении состояния входов(выходов), то наследуйтесь от класса IONotifyController.
Эти классы объявляют минимальный(базовый) интерфейс для IOController-ов, который вы можете расширять. Эти классы объявляют минимальный(базовый) интерфейс для IOController-ов, который вы можете расширять.
...@@ -17,7 +17,7 @@ ...@@ -17,7 +17,7 @@
\section pgIONC_secDeclareIDL Объявление интерфейса на IDL \section pgIONC_secDeclareIDL Объявление интерфейса на IDL
\note Написание интерфейса на IDL требуется, только если вам необходимо расширить базовый набор \note Написание интерфейса на IDL требуется, только если вам необходимо расширить базовый набор
IDL-функций. Все функции обяъвленные здесь станут доступны внешним объекта (локальныйм и удалённым). IDL-функций. Все функции объявленные здесь станут доступны внешним объекта (локальным и удалённым).
При написании интерфейса на IDL действуют те же правила, а именно наследование от соответствующего интерфейса. При написании интерфейса на IDL действуют те же правила, а именно наследование от соответствующего интерфейса.
Пример объявления: Пример объявления:
...@@ -48,7 +48,7 @@ ...@@ -48,7 +48,7 @@
На основе этих файлов вы реализуете свой интерфейс на С++. На основе этих файлов вы реализуете свой интерфейс на С++.
\section pgIONC_secImplementation Реализация интерфейса на C++ \section pgIONC_secImplementation Реализация интерфейса на C++
Необходимо создать класс реализующий объявленный интерфейс. Формирование названия класса и правила наследования Необходимо создать класс реализующий объявленый интерфейс. Формирование названия класса и правила наследования
см. \ref UniSetLibStylePage. см. \ref UniSetLibStylePage.
\par \par
Базовые функции интерфейса IONotifyController_i уже реализованы в классе IONotifyController. Поэтому остается только Базовые функции интерфейса IONotifyController_i уже реализованы в классе IONotifyController. Поэтому остается только
...@@ -72,11 +72,11 @@ ...@@ -72,11 +72,11 @@
MyNotifyController( ObjectId id ); MyNotifyController( ObjectId id );
~MyNotifyController(); ~MyNotifyController();
// ------- функции объевленные в IDL(интерфейс данного объекта) --------- // ------- функции объявленые в IDL(интерфейс данного объекта) ---------
virtual MyNotifyController_i::CardIOTypes getCardIOType(); virtual MyNotifyController_i::CardIOTypes getCardIOType();
// ------- обязательные для реализации функции ------------------------- // ------- обязательные для реализации функции -------------------------
// т.к. они объявленны в базовых классах как чисто виртуальные // т.к. они объявлены в базовых классах как чисто виртуальные
virtual void processingMessage( UniSetTypes::VoidMessage *msg); virtual void processingMessage( UniSetTypes::VoidMessage *msg);
virtual void setState( ObjectId id, CORBA::Boolean state); virtual void setState( ObjectId id, CORBA::Boolean state);
...@@ -180,7 +180,7 @@ ...@@ -180,7 +180,7 @@
\section pgIONC_secLT_Object Создание автономного процесса, не зависящего от TimerService-а \section pgIONC_secLT_Object Создание автономного процесса, не зависящего от TimerService-а
Для повышения автономности работы, можно создать процесс, который сам будет реализовывать таймеры. Для повышения автономности работы, можно создать процесс, который сам будет реализовывать таймеры.
Для этого достаточно при создании своего процесса наследоватся не от IONotifyController, а от IONotifyController_LT. Для этого достаточно при создании своего процесса наследоваться не от IONotifyController, а от IONotifyController_LT.
Т.е. код будет выглядеть так: Т.е. код будет выглядеть так:
\code \code
... ...
......
...@@ -11,7 +11,7 @@ ...@@ -11,7 +11,7 @@
\section subRegCommon Вводная \section subRegCommon Вводная
При наследовании от UniSetObject (и его потомков) регистрация в репозитории происходит автоматически. При наследовании от UniSetObject (и его потомков) регистрация в репозитории происходит автоматически.
Поэтому регистрироватся отдельно нет необходимости. Поэтому регистрироваться отдельно нет необходимости.
\section subReg Регистрация \section subReg Регистрация
...@@ -41,7 +41,7 @@ ...@@ -41,7 +41,7 @@
} }
cacth(ORepFailed) cacth(ORepFailed)
{ {
cerr << "Не удалось зарегестировать объект " << endl; cerr << "Не удалось зарегистрировать объект " << endl;
} }
\endcode \endcode
......
...@@ -12,10 +12,10 @@ ...@@ -12,10 +12,10 @@
\section OMAP_secCommon Общее описание карты объектов \section OMAP_secCommon Общее описание карты объектов
Карта объектов задает индентификаторы объектов, узлов сети и координаты их размещения в репозитории. Карта объектов задает идентификаторы объектов, узлов сети и координаты их размещения в репозитории.
Идентификатор объекта должен быть уникальным в пределах одного узла. Идентификатор объекта должен быть уникальным в пределах одного узла.
Идентификаторы являются неотрицательными числами, что \a минимизирует и \a упрощает передачу по Идентификаторы являются неотрицательными числами, что \a минимизирует и \a упрощает передачу по
сетям раздичного типа (ethernet, CAN, profibus и т.п.). Хотя в использовании конечно удобнее сетям различного типа (ethernet, CAN, profibus и т.п.). Хотя в использовании конечно удобнее
применять текстовые строки. применять текстовые строки.
В данной реализации возможно использовать два способа задания карты объектов В данной реализации возможно использовать два способа задания карты объектов
...@@ -25,7 +25,7 @@ ...@@ -25,7 +25,7 @@
\section OMAP_secStatic Статическая карта объектов \section OMAP_secStatic Статическая карта объектов
\subsection OMAP_subStatic_Create Создание карты \subsection OMAP_subStatic_Create Создание карты
Статическую карут проще всего создать на основе препроцессора. Статическую карту проще всего создать на основе препроцессора.
\par ObjectsMap.h \par ObjectsMap.h
Заголовочный файл формируется при помощи препроцессора на основе файла ObjectsMapSource.h. Заголовочный файл формируется при помощи препроцессора на основе файла ObjectsMapSource.h.
...@@ -98,7 +98,7 @@ const UniSetTypes::ObjectInfo ObjectsMap[MAX_NUMOBJECTS] = ...@@ -98,7 +98,7 @@ const UniSetTypes::ObjectInfo ObjectsMap[MAX_NUMOBJECTS] =
\par ObjectsMapSource.h \par ObjectsMapSource.h
Это собственно карта объектов, в которой прописываеются все объекты имеющие уникальные идентификаторы. Это собственно карта объектов, в которой прописываются все объекты имеющие уникальные идентификаторы.
\code \code
// Sensors // Sensors
...@@ -154,7 +154,7 @@ const UniSetTypes::ObjectInfo ObjectsMap[MAX_NUMOBJECTS] = ...@@ -154,7 +154,7 @@ const UniSetTypes::ObjectInfo ObjectsMap[MAX_NUMOBJECTS] =
\subsection OMAP_subStatic_Node Настройка узлов сети \subsection OMAP_subStatic_Node Настройка узлов сети
Для того чтобы задать узлы сети помимо идентификатора необходимо внести информацию о них в настройки CORB-ы("omniORB.cfg"). Для того чтобы задать узлы сети помимо идентификатора необходимо внести информацию о них в настройки CORB-ы("omniORB.cfg").
Если узел доступен по нескольким сетям, то узлы должны называтся (NodeName1...NodeNameX). NodeName - должно совпадать с именем realname в ObjectMap. Если узел доступен по нескольким сетям, то узлы должны называться (NodeName1...NodeNameX). NodeName - должно совпадать с именем realname в ObjectMap.
В ObjectsMap вносится только имя NodeName1(основной сети), остальные вносятся \b только в конф. файл. В ObjectsMap вносится только имя NodeName1(основной сети), остальные вносятся \b только в конф. файл.
При этом в UniversalInterface::resolve() автоматически будет пытаться связаться с другими узлами используя При этом в UniversalInterface::resolve() автоматически будет пытаться связаться с другими узлами используя
резервные каналы NodeName2...NodeNameX. резервные каналы NodeName2...NodeNameX.
...@@ -190,7 +190,7 @@ const UniSetTypes::ObjectInfo ObjectsMap[MAX_NUMOBJECTS] = ...@@ -190,7 +190,7 @@ const UniSetTypes::ObjectInfo ObjectsMap[MAX_NUMOBJECTS] =
и \a ObjectsMap.cc (содержащий массив. Этот файл необходимо компилировать). и \a ObjectsMap.cc (содержащий массив. Этот файл необходимо компилировать).
\par \par
При использовании статического способа в функции \a main при создании Configure используйте При использовании статического способа в функции \a main при создании Configure используйте
слудующий способ: следующий способ:
\code \code
\#include <Configure.h> \#include <Configure.h>
\#include <ObjectsActivator.h> \#include <ObjectsActivator.h>
......
/* OBSOLETE DOC!!! /* OBSOLETE DOC!!!
\page UniversalInterfacePage Универсальный интерфейс \page UniversalInterfacePage Универсальный интерфейс
Этот интерфейс позволяет получать доступ к объекту по индентификатору(или имени), заказывать датчики, и т.п. Этот интерфейс позволяет получать доступ к объекту по идентификатору(или имени), заказывать датчики, и т.п.
Для работы с удаленными объктами необходимо указывать идентификатор узла, на котором Для работы с удаленными объектами необходимо указывать идентификатор узла, на котором
находится этот объект(если он не задан, идет обращение к локальному). находится этот объект(если он не задан, идет обращение к локальному).
- \ref secIOControl - \ref secIOControl
......
...@@ -20,26 +20,26 @@ ...@@ -20,26 +20,26 @@
\section secSection1 Назначение \section secSection1 Назначение
Библиотека предназначена для разработки распределенных систем управления. В ней собраны основные компоненты из которых Библиотека предназначена для разработки распределенных систем управления. В ней собраны основные компоненты из которых
строятся подобные системы (базовые интерфейсы для разработки процессов управления, процессов управления вводом/выводом, строятся подобные системы (базовые интерфейсы для разработки процессов управления, процессов управления вводом/выводом,
менеджеров сообщений и т.п.). Любую систему управления можно поделить на относительно независимые объекты рещающие менеджеров сообщений и т.п.). Любую систему управления можно поделить на относительно независимые объекты решающие
следующие задачи: следующие задачи:
- ввод/вывод (опрос физических датчиков, обмен с другими устройствами) - ввод/вывод (опрос физических датчиков, обмен с другими устройствами)
- алгоритмы управления тем или иным устройстов или группой устройств - алгоритмы управления тем или иным устройств или группой устройств
- отображение информации (графический интерфейс пользователя) - отображение информации (графический интерфейс пользователя)
- накопление и хранение информации - накопление и хранение информации
- просмотр накопленной информации - просмотр накопленной информации
\par \par
Для каждой из задач в библиотеке разработан определенный компонент(группа компонентов). Для каждой из задач в библиотеке разработан определенный компонент(группа компонентов).
И разработаны универсальные механизмы взаимдействия объектов между собой. И разработаны универсальные механизмы взаимодействия объектов между собой.
\section secSection2 Общие принципы работы \section secSection2 Общие принципы работы
Библиотека позволяет объектам системы обмениватся сообщениями, а так же непосредственно вызывать функции друг-друга. В системе объектами Библиотека позволяет объектам системы обмениваться сообщениями, а так же непосредственно вызывать функции друг-друга. В системе объектами
управляют менеджеры. Которые позволяют управлять (через этот) менеджер сразу набором подчиненных ему объектов. Менеджер может управляют менеджеры. Которые позволяют управлять (через этот) менеджер сразу набором подчиненных ему объектов. Менеджер может
содержать в себе в качестве подчиненного объекта другой менеджер, что позволяет строить довольно гибкую иерархическую структуру содержать в себе в качестве подчиненного объекта другой менеджер, что позволяет строить довольно гибкую иерархическую структуру
управления. Всё взаимодейтсвие объектов( сетевое и межпроцессовое) строится на базе CORBA-ы. управления. Всё взаимодействие объектов( сетевое и межпроцессовое) строится на базе CORBA-ы.
\subsection subTransfer Взаимодействие объектов системы \subsection subTransfer Взаимодействие объектов системы
Взаимодействие объектов между собой происходит через ObjectRepository. Каждый объект становится доступным другим объектам только Взаимодействие объектов между собой происходит через ObjectRepository. Каждый объект становится доступным другим объектам только
после регистрации в репозитории. Для получения доступа к другому объекту (даже удаленному) необхоимо знать его идентификатор(UniSetTypes::ObjectId) после регистрации в репозитории. Для получения доступа к другому объекту (даже удаленному) необходимо знать его идентификатор(UniSetTypes::ObjectId)
и при помощи репозитория получить на него ссылку, с которой можно работать как с указателем на объект. и при помощи репозитория получить на него ссылку, с которой можно работать как с указателем на объект.
... ...
Каждый узел по возможности должен работать с максимальной автономностью. Т.е. все основные сервисы (TimerService, InfoServer, DBServer) Каждый узел по возможности должен работать с максимальной автономностью. Т.е. все основные сервисы (TimerService, InfoServer, DBServer)
...@@ -60,25 +60,25 @@ ...@@ -60,25 +60,25 @@
Это унифицированный интерфейс для сохранения и получения информации о состоянии дискретных и Это унифицированный интерфейс для сохранения и получения информации о состоянии дискретных и
аналоговых датчиков. аналоговых датчиков.
\par IONotifyController \par IONotifyController
Раширение IOController-а. Предоставляющее интерфейс для заказа уведомлений об изменении состояния датчиков. Расширение IOController-а. Предоставляющее интерфейс для заказа уведомлений об изменении состояния датчиков.
\subsection UniSetGraphics Графический интерфейс пользователя \subsection UniSetGraphics Графический интерфейс пользователя
... ...
\subsection UniDiag Просмотр накопленной информации \subsection UniDiag Просмотр накопленной информации
Для большей универсальности слежение за работой системы, диагностирование и просмотр накопленной информации Для большей универсальности слежение за работой системы, диагностирование и просмотр накопленной информации
сделаны в виде web-интерфейса написанного на PHP. \a в \a процессе \a разработаки... сделаны в виде web-интерфейса написанного на PHP. \a в \a процессе \a разработки...
\section secDetail Подробности \section secDetail Подробности
\subsection subObjects Объекты, Менеджеры, Активаторы \subsection subObjects Объекты, Менеджеры, Активаторы
\par Объекты (UniSetObject) \par Объекты (UniSetObject)
Объекты являются пасивными единицами, так как не могут функционировать без менеджера или активатора. Для того, чтобы объект Объекты являются пассивными единицами, так как не могут функционировать без менеджера или активатора. Для того, чтобы объект
мог принимать сообщения и предоставлять свои функции другим объектам он должен быть зарегистрирован в менеджере объектов мог принимать сообщения и предоставлять свои функции другим объектам он должен быть зарегистрирован в менеджере объектов
(ObjectsManager) или напрямую в активаторе (ObjectsActivator) при помощи функции ObjectsManager::addObject(...). (ObjectsManager) или напрямую в активаторе (ObjectsActivator) при помощи функции ObjectsManager::addObject(...).
\par Менеджеры (ObjectsManager) \par Менеджеры (ObjectsManager)
Менеджеры используются для управления сразу группой объектов, а также сами являются объектами и могут быть Менеджеры используются для управления сразу группой объектов, а также сами являются объектами и могут быть
зарегитстрированы в другом менеджере (или активаторе). Они тоже являются пасивными единицами, так как не могут функционировать без зарегистрированы в другом менеджере (или активаторе). Они тоже являются пассивными единицами, так как не могут функционировать без
активатора. активатора.
\par Активаторы (ObjectsActivator) \par Активаторы (ObjectsActivator)
Активатор предназначен для активизации объектов и менеджеров. Он обладает свойствами менеджера (позволяет регистрировать в себе Активатор предназначен для активизации объектов и менеджеров. Он обладает свойствами менеджера (позволяет регистрировать в себе
......
...@@ -46,6 +46,6 @@ ...@@ -46,6 +46,6 @@
\code \code
<item textname="...." iotype="..." ... depend="OtherSensor_AS" depend_value="2" /> <item textname="...." iotype="..." ... depend="OtherSensor_AS" depend_value="2" />
\endcode \endcode
В данном случае подразумевается, что разрещающим датчиком является OtherSensor_AS=2. В данном случае подразумевается, что разрешающим датчиком является OtherSensor_AS=2.
*/ */
...@@ -13,7 +13,7 @@ ...@@ -13,7 +13,7 @@
В основу положена технология CORBA (omniORB - реализация AT&T). В основу положена технология CORBA (omniORB - реализация AT&T).
Но основе вызовов CORBA построено всё взаимодействие. При этом API библиотеки, Но основе вызовов CORBA построено всё взаимодействие. При этом API библиотеки,
"максирует" взаимодействие через CORBA и при необходимости "маскирует" взаимодействие через CORBA и при необходимости
взаимодействие может быть переписано на основе других механизмов. взаимодействие может быть переписано на основе других механизмов.
В библиотеке реализованы наиболее распространённые интерфейсы обмена, В библиотеке реализованы наиболее распространённые интерфейсы обмена,
...@@ -21,7 +21,7 @@ ...@@ -21,7 +21,7 @@
реализующий обмен по протоколу UDP. реализующий обмен по протоколу UDP.
Для взаимодействия с базами данных, реализован базовый DBInterface, Для взаимодействия с базами данных, реализован базовый DBInterface,
на основе которго можно писать интерфейсы для подключения uniset на основе которого можно писать интерфейсы для подключения uniset
к различным СУБД. В самой libuniset реализовано взаимодействие с MySQL. к различным СУБД. В самой libuniset реализовано взаимодействие с MySQL.
Помимо собственно единого интерфейса, в библиотеке реализованы \b "готовые компоненты" Помимо собственно единого интерфейса, в библиотеке реализованы \b "готовые компоненты"
...@@ -29,12 +29,12 @@ ...@@ -29,12 +29,12 @@
- \b SharedMemory - хранение "переменных" - \b SharedMemory - хранение "переменных"
- \b IOControl - работа с картами ввода/вывода - \b IOControl - работа с картами ввода/вывода
- \b Modbus TCP/RTU slave и master режимы - \b Modbus TCP/RTU slave и master режимы
- \b UNetExchange - взаимодецствие по протоколу UDP - \b UNetExchange - взаимодействие по протоколу UDP
- \b LogicProcessor - компонент, позволяющий описывать алгоритмы на основе, логических схем - \b LogicProcessor - компонент, позволяющий описывать алгоритмы на основе, логических схем
(записываемых в xml-файле). (записываемых в xml-файле).
\b Готовые \b компоненты - представляют из себя уже законченные программы (процессы), \b Готовые \b компоненты - представляют из себя уже законченные программы (процессы),
которые "умеют" взаимодейсвовать с SharedMemory и позволяют легко которые "умеют" взаимодействовать с SharedMemory и позволяют легко
"развёртывать" распределённые системы. "развёртывать" распределённые системы.
Всё взаимодействие в libuniset построено на понятии "датчик". Это некоторая Всё взаимодействие в libuniset построено на понятии "датчик". Это некоторая
...@@ -58,10 +58,10 @@ ...@@ -58,10 +58,10 @@
Все процессы условно можно разделить на два типа \b "активные" и \b "пассивные". Все процессы условно можно разделить на два типа \b "активные" и \b "пассивные".
\b Пассивные процессы - это процессы которые большую часть времени "спят" ожидая, \b Пассивные процессы - это процессы которые большую часть времени "спят" ожидая,
событий изменения датчиков. В основном к таким процессам относяться процессы управления. событий изменения датчиков. В основном к таким процессам относятся процессы управления.
\b Активные процессы - это процессы которые постоянно выполняют какую-то работу. \b Активные процессы - это процессы которые постоянно выполняют какую-то работу.
К таким процессам относяться: К таким процессам относятся:
- процессы обмена по сети (в данном случае CAN) - процессы обмена по сети (в данном случае CAN)
- процессы работы с картами ввода/вывода (IOControl) - процессы работы с картами ввода/вывода (IOControl)
- процессы обмена с какими-то внешними устройствами (RS485 или ModbusTCP) - процессы обмена с какими-то внешними устройствами (RS485 или ModbusTCP)
...@@ -87,10 +87,10 @@ ...@@ -87,10 +87,10 @@
Для обеспечения \b "прозрачности сети" всё взаимодействие построено на Для обеспечения \b "прозрачности сети" всё взаимодействие построено на
использовании \b SharedMemory \b(SM), хранящей состояние датчиков во \b ВСЕЙ системе. использовании \b SharedMemory \b(SM), хранящей состояние датчиков во \b ВСЕЙ системе.
При этом на каждом узле запускатся своя копия \b SM. "прозрачность" при этом При этом на каждом узле запускаться своя копия \b SM. "прозрачность" при этом
обеспечивают процессы обмена между узлами по соответствующему протоколу обеспечивают процессы обмена между узлами по соответствующему протоколу
(на рисунке это CAN и UNET). Узлы \b постоянно обмениваются между собой (на рисунке это CAN и UNET). Узлы \b постоянно обмениваются между собой
датчиками обеспечивая \b "одинаковостть" хранимой в SM информации. датчиками обеспечивая \b "одинаковость" хранимой в SM информации.
Каждый процесс обмена получает от других узлов информацию о находящихся у них датчиков, Каждый процесс обмена получает от других узлов информацию о находящихся у них датчиков,
и в свою очередь посылает другим узлам информацию о датчиках находящихся у него на узле. и в свою очередь посылает другим узлам информацию о датчиках находящихся у него на узле.
......
...@@ -4,16 +4,16 @@ ...@@ -4,16 +4,16 @@
-# утилиты мониторинга работы системы -# утилиты мониторинга работы системы
-# настройку "политик" для ORB сделать из конф. файла -# настройку "политик" для ORB сделать из конф. файла
-# по максимуму переход на xml -# по максимуму переход на xml
-# дополнить описание IOController-ов разделом про XML-файл заказчков(создание,работа) -# дополнить описание IOController-ов разделом про XML-файл заказчиков(создание,работа)
-# сделать описание принципов и деталей межобъектного взаимодействия -# сделать описание принципов и деталей межобъектного взаимодействия
(об ограничениях на размер сообщений, очередь сообщений, приоритеты и т.п.) (об ограничениях на размер сообщений, очередь сообщений, приоритеты и т.п.)
-# попытатся сделать работу с сервисами более универсальной -# попытаться сделать работу с сервисами более универсальной
(что то типа "UniSetTypes::ObjectId conf->getService(const string name)" ) (что то типа "UniSetTypes::ObjectId conf->getService(const string name)" )
-# откорректировать и дописать "общее описание" библиотеки -# откорректировать и дописать "общее описание" библиотеки
-# сделать тип в UniSetObject::getType string-ом -# сделать тип в UniSetObject::getType string-ом
(для универсальности и простоты будущих расширений) (для универсальности и простоты будущих расширений)
-# переписать тестовые примеры, под текущую ситуацию. -# переписать тестовые примеры, под текущую ситуацию.
-# в будущем попытатся отказатся от ObjectId и перейти на строки (это надо ещё обдумать) -# в будущем попытаться отказаться от ObjectId и перейти на строки (это надо ещё обдумать)
-# в InfoServer-е по routeList-у сообщения пересылаются, только если они локальные. -# в InfoServer-е по routeList-у сообщения пересылаются, только если они локальные.
Надо переделать механизм, чтобы можно было отделять тех кому пересылать все сообщения, Надо переделать механизм, чтобы можно было отделять тех кому пересылать все сообщения,
от тех кому пересылать только локальные.... от тех кому пересылать только локальные....
......
<?xml version = '1.0' encoding = 'koi8-r' ?> <?xml version = '1.0' encoding = 'koi8-r' ?>
<UNISETPLC> <UNISETPLC>
<UserData></UserData> <UserData></UserData>
<!-- Общие(стартовые) параметры по UniSet --> <!-- Общие (стартовые) параметры по UniSet -->
<Configure> <Configure>
<NameService host="localhost" port="2817"/> <NameService host="localhost" port="2817"/>
<LocalNode name="LocalhostNode"/> <LocalNode name="LocalhostNode"/>
......
...@@ -42,7 +42,7 @@ namespace uniset ...@@ -42,7 +42,7 @@ namespace uniset
"OpenTSDB" - time series database. Специальная БД оптимизированная "OpenTSDB" - time series database. Специальная БД оптимизированная
для хранения временных рядов (по простому: данных с временными метками). для хранения временных рядов (по простому: данных с временными метками).
Класс реализует пересылку указанных (настроенных) дачиков в БД поддерживающую Класс реализует пересылку указанных (настроенных) датчиков в БД поддерживающую
интерфейс совместимый с OpenTSDB. В текущей реализации используется посылка интерфейс совместимый с OpenTSDB. В текущей реализации используется посылка
строк в формате Telnet строк в формате Telnet
\code \code
...@@ -85,7 +85,7 @@ namespace uniset ...@@ -85,7 +85,7 @@ namespace uniset
\section sec_OpenTSDB_Queue Буфер на запись в БД \section sec_OpenTSDB_Queue Буфер на запись в БД
В данной реализации встроен специальный буфер, который накапливает данные и скидывает их В данной реализации встроен специальный буфер, который накапливает данные и скидывает их
пачкой в БД. Так же он является защитным механизом на случай если БД временно недоступна. пачкой в БД. Так же он является защитным механизмом на случай если БД временно недоступна.
Параметры буфера задаются аргументами командной строки или в конфигурационном файле. Параметры буфера задаются аргументами командной строки или в конфигурационном файле.
Доступны следующие параметры: Доступны следующие параметры:
- \b bufSize - размер буфера, при заполнении которого происходит посылка данных в БД - \b bufSize - размер буфера, при заполнении которого происходит посылка данных в БД
......
...@@ -41,19 +41,19 @@ namespace uniset ...@@ -41,19 +41,19 @@ namespace uniset
\section sec_DBS_Comm Общее описание работы DBServer_MySQL \section sec_DBS_Comm Общее описание работы DBServer_MySQL
Сервис предназначен для работы с БД MySQL. В его задачи входит Сервис предназначен для работы с БД MySQL. В его задачи входит
сохранение всех событий происходищих в системе в БД. К этим сохранение всех событий происходящих в системе в БД. К этим
событиям относятся изменение состояния датчиков, различные логи событиям относятся изменение состояния датчиков, различные логи
работы процессов и т.п. работы процессов и т.п.
К моменту запуска, подразумевается, что неободимые таблицы уже К моменту запуска, подразумевается, что необходимые таблицы уже
созданы, все необходимые настройки mysql сделаны. созданы, все необходимые настройки mysql сделаны.
\par \par
При работе с БД, сервис в основном пишет в БД. Обработка накопленных данных При работе с БД, сервис в основном пишет в БД. Обработка накопленных данных
ведётся уже другими программами (web-интерфейс). ведётся уже другими программами (web-интерфейс).
\par \par
Для повышения надежности DBServer переодически ( DBServer_MySQL::PingTimer ) проверяет наличие связи с сервером БД. Для повышения надежности DBServer периодически ( DBServer_MySQL::PingTimer ) проверяет наличие связи с сервером БД.
В случае если связь пропала (или не была установлена при старте) DBServer пытается вновь каждые DBServer::ReconnectTimer В случае если связь пропала (или не была установлена при старте) DBServer пытается вновь каждые DBServer::ReconnectTimer
произвести соединение. При этом все запросы которые поступают для запии в БД, но не мгут быть записаны складываются произвести соединение. При этом все запросы которые поступают для записи в БД, но не могут быть записаны складываются
в буфер (см. \ref sec_DBS_Buffer). в буфер (см. \ref sec_DBS_Buffer).
\warning При каждой попытке восстановить соединение DBServer заново читает конф. файл. Поэтому он может подхватить \warning При каждой попытке восстановить соединение DBServer заново читает конф. файл. Поэтому он может подхватить
новые настройки. новые настройки.
...@@ -73,14 +73,14 @@ namespace uniset ...@@ -73,14 +73,14 @@ namespace uniset
\section sec_DBS_Buffer Защита от потери данных \section sec_DBS_Buffer Защита от потери данных
Для того, чтобы на момент отсутствия связи с БД данные по возможности не потерялись, Для того, чтобы на момент отсутствия связи с БД данные по возможности не потерялись,
сделан "кольцевой" буфер. Размер которго можно регулировать параметром "--dbserver-buffer-size" сделан "кольцевой" буфер. Размер которого можно регулировать параметром "--dbserver-buffer-size"
или параметром \b bufferSize=".." в конфигурационном файле секции "<LocalDBSErver...>". или параметром \b bufferSize=".." в конфигурационном файле секции "<LocalDBSErver...>".
Механизм построен на том, что если связь с mysql сервером отсутствует или пропала, Механизм построен на том, что если связь с mysql сервером отсутствует или пропала,
то сообщения помещаются в колевой буфер, который "опустошается" как только она восстановится. то сообщения помещаются в нулевой буфер, который "опустошается" как только она восстановится.
Если связь не восстановилась, а буфер достиг максимального заданного размера, то удаляются Если связь не восстановилась, а буфер достиг максимального заданного размера, то удаляются
более ранние сообщения. Эту логику можно сменить, если указать параметр "--dbserver-buffer-last-remove" более ранние сообщения. Эту логику можно сменить, если указать параметр "--dbserver-buffer-last-remove"
или \b bufferLastRemove="1", то терятся будут сообщения добавляемые в конец. или \b bufferLastRemove="1", то теряться будут сообщения добавляемые в конец.
\section sec_DBS_Tables Таблицы MySQL \section sec_DBS_Tables Таблицы MySQL
К основным таблицам относятся следующие: К основным таблицам относятся следующие:
...@@ -180,7 +180,7 @@ namespace uniset ...@@ -180,7 +180,7 @@ namespace uniset
enum Timers enum Timers
{ {
PingTimer, /*!< таймер на переодическую проверку соединения с сервером БД */ PingTimer, /*!< таймер на пере одическую проверку соединения с сервером БД */
ReconnectTimer, /*!< таймер на повторную попытку соединения с сервером БД (или восстановления связи) */ ReconnectTimer, /*!< таймер на повторную попытку соединения с сервером БД (или восстановления связи) */
lastNumberOfTimer lastNumberOfTimer
}; };
...@@ -188,7 +188,7 @@ namespace uniset ...@@ -188,7 +188,7 @@ namespace uniset
std::unique_ptr<MySQLInterface> db; std::unique_ptr<MySQLInterface> db;
int PingTime = { 15000 }; int PingTime = { 15000 };
int ReconnectTime = { 30000 }; int ReconnectTime = { 30000 };
bool connect_ok = { false }; /*! признак наличия соеднинения с сервером БД */ bool connect_ok = { false }; /*! признак наличия соединения с сервером БД */
bool activate = { false }; bool activate = { false };
......
...@@ -59,7 +59,7 @@ namespace uniset ...@@ -59,7 +59,7 @@ namespace uniset
/*! /*!
проверка связи с БД. проверка связи с БД.
в случае отсутсвия попытка восстановить... в случае отсутствия попытка восстановить...
*/ */
virtual bool ping() const override; virtual bool ping() const override;
......
...@@ -45,7 +45,7 @@ namespace uniset ...@@ -45,7 +45,7 @@ namespace uniset
* Во первых надо иметь ввиду, что буфер - это то, что потеряется если вдруг произойдёт сбой * Во первых надо иметь ввиду, что буфер - это то, что потеряется если вдруг произойдёт сбой
* по питанию или программа вылетит. Поэтому если он большой, то будет потеряно много данных. * по питанию или программа вылетит. Поэтому если он большой, то будет потеряно много данных.
* И второе, т.к. это vector - то идёт выделение "непрерывного куска памяти", поэтому у ОС могут * И второе, т.к. это vector - то идёт выделение "непрерывного куска памяти", поэтому у ОС могут
* быть проблеммы найти "большой непрерывный кусок". * быть проблемы найти "большой непрерывный кусок".
* Тем не менее реализация сделана на vector-е чтобы избежать лишних "перевыделений" (и сегментации) памяти во время работы. * Тем не менее реализация сделана на vector-е чтобы избежать лишних "перевыделений" (и сегментации) памяти во время работы.
* *
* \warning Временно, для обратной совместимости поле 'time_usec' в таблицах оставлено с таким названием, * \warning Временно, для обратной совместимости поле 'time_usec' в таблицах оставлено с таким названием,
...@@ -100,7 +100,7 @@ namespace uniset ...@@ -100,7 +100,7 @@ namespace uniset
enum Timers enum Timers
{ {
PingTimer, /*!< таймер на переодическую проверку соединения с сервером БД */ PingTimer, /*!< таймер на пере одическую проверку соединения с сервером БД */
ReconnectTimer, /*!< таймер на повторную попытку соединения с сервером БД (или восстановления связи) */ ReconnectTimer, /*!< таймер на повторную попытку соединения с сервером БД (или восстановления связи) */
FlushInsertBuffer, /*!< таймер на сброс Insert-буфера */ FlushInsertBuffer, /*!< таймер на сброс Insert-буфера */
lastNumberOfTimer lastNumberOfTimer
...@@ -127,7 +127,7 @@ namespace uniset ...@@ -127,7 +127,7 @@ namespace uniset
int PingTime = { 15000 }; int PingTime = { 15000 };
int ReconnectTime = { 30000 }; int ReconnectTime = { 30000 };
bool connect_ok = { false }; /*! признак наличия соеднинения с сервером БД */ bool connect_ok = { false }; /*! признак наличия соединения с сервером БД */
QueryBuffer qbuf; QueryBuffer qbuf;
size_t qbufSize = { 200 }; // размер буфера сообщений. size_t qbufSize = { 200 }; // размер буфера сообщений.
...@@ -138,7 +138,7 @@ namespace uniset ...@@ -138,7 +138,7 @@ namespace uniset
size_t ibufSize = { 0 }; size_t ibufSize = { 0 };
size_t ibufMaxSize = { 2000 }; size_t ibufMaxSize = { 2000 };
timeout_t ibufSyncTimeout = { 15000 }; timeout_t ibufSyncTimeout = { 15000 };
float ibufOverflowCleanFactor = { 0.5 }; // коэфициент {0...1} чистки буфера при переполнении float ibufOverflowCleanFactor = { 0.5 }; // коэффициент {0...1} чистки буфера при переполнении
}; };
// ---------------------------------------------------------------------------------- // ----------------------------------------------------------------------------------
} // end of namespace uniset } // end of namespace uniset
......
...@@ -41,19 +41,19 @@ namespace uniset ...@@ -41,19 +41,19 @@ namespace uniset
\section sec_DBS_Comm Общее описание работы DBServer_SQLite \section sec_DBS_Comm Общее описание работы DBServer_SQLite
Сервис предназначен для работы с БД SQLite. В его задачи входит Сервис предназначен для работы с БД SQLite. В его задачи входит
сохранение всех событий происходищих в системе в БД. К этим сохранение всех событий происходящих в системе в БД. К этим
событиям относятся изменение состояния датчиков, различные логи событиям относятся изменение состояния датчиков, различные логи
работы процессов и т.п. работы процессов и т.п.
К моменту запуска, подразумевается, что неободимые таблицы уже К моменту запуска, подразумевается, что необходимые таблицы уже
созданы, все необходимые настройки mysql сделаны. созданы, все необходимые настройки mysql сделаны.
\par \par
При работе с БД, сервис в основном пишет в БД. Обработка накопленных данных При работе с БД, сервис в основном пишет в БД. Обработка накопленных данных
ведётся уже другими программами (web-интерфейс). ведётся уже другими программами (web-интерфейс).
\par \par
Для повышения надежности DBServer переодически ( DBServer_SQLite::PingTimer ) проверяет наличие связи с сервером БД. Для повышения надежности DBServer периодически ( DBServer_SQLite::PingTimer ) проверяет наличие связи с сервером БД.
В случае если связь пропала (или не была установлена при старте) DBServer пытается вновь каждые DBServer::ReconnectTimer В случае если связь пропала (или не была установлена при старте) DBServer пытается вновь каждые DBServer::ReconnectTimer
произвести соединение. При этом все запросы которые поступают для запии в БД, но не мгут быть записаны складываются произвести соединение. При этом все запросы которые поступают для записи в БД, но не могут быть записаны складываются
в буфер (см. \ref sec_DBS_Buffer). в буфер (см. \ref sec_DBS_Buffer).
\warning При каждой попытке восстановить соединение DBServer заново читает конф. файл. Поэтому он может подхватить \warning При каждой попытке восстановить соединение DBServer заново читает конф. файл. Поэтому он может подхватить
новые настройки. новые настройки.
...@@ -73,14 +73,14 @@ namespace uniset ...@@ -73,14 +73,14 @@ namespace uniset
\section sec_DBS_Buffer Защита от потери данных \section sec_DBS_Buffer Защита от потери данных
Для того, чтобы на момент отсутствия связи с БД данные по возможности не потерялись, Для того, чтобы на момент отсутствия связи с БД данные по возможности не потерялись,
сделан "кольцевой" буфер. Размер которго можно регулировать параметром "--dbserver-buffer-size" сделан "кольцевой" буфер. Размер которого можно регулировать параметром "--dbserver-buffer-size"
или параметром \b bufferSize=".." в конфигурационном файле секции "<LocalDBSErver...>". или параметром \b bufferSize=".." в конфигурационном файле секции "<LocalDBSErver...>".
Механизм построен на том, что если связь с mysql сервером отсутствует или пропала, Механизм построен на том, что если связь с mysql сервером отсутствует или пропала,
то сообщения помещаются в колевой буфер, который "опустошается" как только она восстановится. то сообщения помещаются в нулевой буфер, который "опустошается" как только она восстановится.
Если связь не восстановилась, а буфер достиг максимального заданного размера, то удаляются Если связь не восстановилась, а буфер достиг максимального заданного размера, то удаляются
более ранние сообщения. Эту логику можно сменить, если указать параметр "--dbserver-buffer-last-remove" более ранние сообщения. Эту логику можно сменить, если указать параметр "--dbserver-buffer-last-remove"
или \b bufferLastRemove="1", то терятся будут сообщения добавляемые в конец. или \b bufferLastRemove="1", то теряться будут сообщения добавляемые в конец.
\section sec_DBS_Tables Таблицы SQLite \section sec_DBS_Tables Таблицы SQLite
К основным таблицам относятся следующие (описание в формате MySQL!): К основным таблицам относятся следующие (описание в формате MySQL!):
...@@ -180,7 +180,7 @@ namespace uniset ...@@ -180,7 +180,7 @@ namespace uniset
enum Timers enum Timers
{ {
PingTimer, /*!< таймер на переодическую проверку соединения с сервером БД */ PingTimer, /*!< таймер на пере одическую проверку соединения с сервером БД */
ReconnectTimer, /*!< таймер на повторную попытку соединения с сервером БД (или восстановления связи) */ ReconnectTimer, /*!< таймер на повторную попытку соединения с сервером БД (или восстановления связи) */
lastNumberOfTimer lastNumberOfTimer
}; };
...@@ -189,7 +189,7 @@ namespace uniset ...@@ -189,7 +189,7 @@ namespace uniset
int PingTime = { 300000 }; int PingTime = { 300000 };
int ReconnectTime = { 180000 }; int ReconnectTime = { 180000 };
bool connect_ok = { false }; /*! признак наличия соеднинения с сервером БД */ bool connect_ok = { false }; /*! признак наличия соединения с сервером БД */
bool activate = { false }; bool activate = { false };
typedef std::queue<std::string> QueryBuffer; typedef std::queue<std::string> QueryBuffer;
......
...@@ -1261,7 +1261,7 @@ namespace uniset ...@@ -1261,7 +1261,7 @@ namespace uniset
cout << " Разрешены: TBI0_24,TBI24_0,TBI16_8" << endl; cout << " Разрешены: TBI0_24,TBI24_0,TBI16_8" << endl;
cout << "--prefix-default_cardnum - Номер карты по умолчанию. По умолчанию -1." << endl; cout << "--prefix-default_cardnum - Номер карты по умолчанию. По умолчанию -1." << endl;
cout << " Если задать, то он будет использоватся для датчиков" << endl; cout << " Если задать, то он будет использоваться для датчиков" << endl;
cout << " у которых не задано поле 'card'." << endl; cout << " у которых не задано поле 'card'." << endl;
cout << "--prefix-test-lamp - Для данного узла в качестве датчика кнопки 'ТестЛамп' использовать указанный датчик." << endl; cout << "--prefix-test-lamp - Для данного узла в качестве датчика кнопки 'ТестЛамп' использовать указанный датчик." << endl;
...@@ -1274,7 +1274,7 @@ namespace uniset ...@@ -1274,7 +1274,7 @@ namespace uniset
cout << "--prefix-blink-time msec - Частота мигания, мсек. По умолчанию в configure.xml" << endl; cout << "--prefix-blink-time msec - Частота мигания, мсек. По умолчанию в configure.xml" << endl;
cout << "--prefix-blink2-time msec - Вторая частота мигания (lmpBLINK2), мсек. По умолчанию в configure.xml" << endl; cout << "--prefix-blink2-time msec - Вторая частота мигания (lmpBLINK2), мсек. По умолчанию в configure.xml" << endl;
cout << "--prefix-blink3-time msec - Вторая частота мигания (lmpBLINK3), мсек. По умолчанию в configure.xml" << endl; cout << "--prefix-blink3-time msec - Вторая частота мигания (lmpBLINK3), мсек. По умолчанию в configure.xml" << endl;
cout << "--prefix-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-дачиком." << endl; cout << "--prefix-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-датчиком." << endl;
cout << "--prefix-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl; cout << "--prefix-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl;
cout << "--prefix-ready-timeout - Время ожидания готовности SM к работе, мсек. (-1 - ждать 'вечно')" << endl; cout << "--prefix-ready-timeout - Время ожидания готовности SM к работе, мсек. (-1 - ждать 'вечно')" << endl;
cout << "--prefix-force - Сохранять значения в SM, независимо от, того менялось ли значение" << endl; cout << "--prefix-force - Сохранять значения в SM, независимо от, того менялось ли значение" << endl;
......
...@@ -74,7 +74,7 @@ namespace uniset ...@@ -74,7 +74,7 @@ namespace uniset
Разрешены: TBI0_24,TBI24_0,TBI16_8 Разрешены: TBI0_24,TBI24_0,TBI16_8
<br>\b --io-default_cardnum - Номер карты по умолчанию. По умолчанию -1. <br>\b --io-default_cardnum - Номер карты по умолчанию. По умолчанию -1.
Если задать, то он будет использоватся для датчиков Если задать, то он будет использоваться для датчиков
у которых не задано поле 'card'. у которых не задано поле 'card'.
<br>\b --io-test-lamp - Для данного узла в качестве датчика кнопки 'ТестЛамп' использовать указанный датчик. <br>\b --io-test-lamp - Для данного узла в качестве датчика кнопки 'ТестЛамп' использовать указанный датчик.
...@@ -87,7 +87,7 @@ namespace uniset ...@@ -87,7 +87,7 @@ namespace uniset
<br>\b --io-blink-time msec - Частота мигания, мсек. По умолчанию в configure.xml <br>\b --io-blink-time msec - Частота мигания, мсек. По умолчанию в configure.xml
<br>\b --io-blink2-time msec - Вторая частота мигания (lmpBLINK2), мсек. По умолчанию в configure.xml <br>\b --io-blink2-time msec - Вторая частота мигания (lmpBLINK2), мсек. По умолчанию в configure.xml
<br>\b --io-blink3-time msec - Вторая частота мигания (lmpBLINK3), мсек. По умолчанию в configure.xml <br>\b --io-blink3-time msec - Вторая частота мигания (lmpBLINK3), мсек. По умолчанию в configure.xml
<br>\b --io-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-дачиком. <br>\b --io-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-датчиком.
<br>\b --io-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10. <br>\b --io-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10.
<br>\b --io-ready-timeout - Время ожидания готовности SM к работе, мсек. (-1 - ждать 'вечно') <br>\b --io-ready-timeout - Время ожидания готовности SM к работе, мсек. (-1 - ждать 'вечно')
<br>\b --io-force - Сохранять значения в SM, независимо от, того менялось ли значение <br>\b --io-force - Сохранять значения в SM, независимо от, того менялось ли значение
...@@ -106,7 +106,7 @@ namespace uniset ...@@ -106,7 +106,7 @@ namespace uniset
но будет его присылать в SensorMessage) но будет его присылать в SensorMessage)
<br>\b cal_nocrop - не обрезать значение по крайним точкам по при калибровке. <br>\b cal_nocrop - не обрезать значение по крайним точкам по при калибровке.
<br>\b breaklim - пороговое значение для определения обырва датчика (используется для AI). <br>\b breaklim - пороговое значение для определения обрыва датчика (используется для AI).
Если значение ниже этого порога, то выставляется признак обрыва датчика. Если значение ниже этого порога, то выставляется признак обрыва датчика.
<br>\b debouncedelay - защита от дребезга. Задержка на дребезг, мсек. <br>\b debouncedelay - защита от дребезга. Задержка на дребезг, мсек.
<br>\b ondelay - задержка на срабатывание, мсек. <br>\b ondelay - задержка на срабатывание, мсек.
...@@ -125,7 +125,7 @@ namespace uniset ...@@ -125,7 +125,7 @@ namespace uniset
<br>\b rmax - максимальное "сырое" значение <br>\b rmax - максимальное "сырое" значение
<br>\b cmin - минимальное "калиброванное" значение <br>\b cmin - минимальное "калиброванное" значение
<br>\b cmax - максимальное "калиброванное" значение <br>\b cmax - максимальное "калиброванное" значение
<br>\b precision - Точность. Задаёт количство знаков после запятой. <br>\b precision - Точность. Задаёт количество знаков после запятой.
<br>Т.е. при считывании из канала, значение домножается <br>Т.е. при считывании из канала, значение домножается
<br>на 10^precision и уже таким сохраняется. <br>на 10^precision и уже таким сохраняется.
<br>А в SensorMessage присылается присылается precision. <br>А в SensorMessage присылается присылается precision.
...@@ -140,8 +140,8 @@ namespace uniset ...@@ -140,8 +140,8 @@ namespace uniset
<br>\b threshold_aid - идентификатор аналогового датчика по которому формируется порог. <br>\b threshold_aid - идентификатор аналогового датчика по которому формируется порог.
Используется для DI. Используется для DI.
<br>\b lowlimit - нижний порого срабатывания. <br>\b lowlimit - нижний порог срабатывания.
<br>\b hilimit - верхний порого срабатывания. <br>\b hilimit - верхний порог срабатывания.
<br>\b card - номер карты <br>\b card - номер карты
<br>\b subdev - номер подустройства <br>\b subdev - номер подустройства
...@@ -170,7 +170,7 @@ namespace uniset ...@@ -170,7 +170,7 @@ namespace uniset
\section sec_IOC_ConfList Список датчиков для процесса в/в \section sec_IOC_ConfList Список датчиков для процесса в/в
\section sec_IOC_TestMode Тестовый режим \section sec_IOC_TestMode Тестовый режим
В IOControl встроена возможнось переводить его в один из тестовых режимов. В IOControl встроена возможность переводить его в один из тестовых режимов.
Для этого необходимо указать для IOControl аналоговый датчик в который будет записан "код" Для этого необходимо указать для IOControl аналоговый датчик в который будет записан "код"
режима работы. Датчик можно задать либо аргументом командной строки режима работы. Датчик можно задать либо аргументом командной строки
--io-test-mode ID либо в конфигурационном файле testmode_as="ID" --io-test-mode ID либо в конфигурационном файле testmode_as="ID"
...@@ -269,7 +269,7 @@ namespace uniset ...@@ -269,7 +269,7 @@ namespace uniset
int channel; /*!< (UNIO) канал [0...23] */ int channel; /*!< (UNIO) канал [0...23] */
int ncard; /*!< номер карты [1|2]. -1 - не определена. */ int ncard; /*!< номер карты [1|2]. -1 - не определена. */
/*! Вид поключения /*! Вид подключения
0 - analog ref = analog ground 0 - analog ref = analog ground
1 - analog ref = analog common 1 - analog ref = analog common
2 - analog ref = differential 2 - analog ref = differential
...@@ -348,7 +348,7 @@ namespace uniset ...@@ -348,7 +348,7 @@ namespace uniset
xmlNode* confnode = { 0 }; /*!< xml-узел в настроечном файле */ xmlNode* confnode = { 0 }; /*!< xml-узел в настроечном файле */
int polltime = { 150 }; /*!< переодичность обновления данных (опроса карт в/в), [мсек] */ int polltime = { 150 }; /*!< периодичность обновления данных (опроса карт в/в), [мсек] */
CardList cards; /*!< список карт - массив созданных ComediInterface */ CardList cards; /*!< список карт - массив созданных ComediInterface */
bool noCards = { false }; bool noCards = { false };
......
...@@ -59,7 +59,7 @@ namespace uniset ...@@ -59,7 +59,7 @@ namespace uniset
virtual void configureChannel( int subdev, int channel, ChannelType type, int range = 0, int aref = 0 ) const override; virtual void configureChannel( int subdev, int channel, ChannelType type, int range = 0, int aref = 0 ) const override;
}; };
// -------------------------------------------------------------------------- // --------------------------------------------------------------------------
/*! Специальный IOControl для тестирвания подменяющий все карты в/в на FakeComediInterface */ /*! Специальный IOControl для тестирования подменяющий все карты в/в на FakeComediInterface */
class FakeIOControl: class FakeIOControl:
public IOControl public IOControl
{ {
......
...@@ -88,7 +88,7 @@ namespace uniset ...@@ -88,7 +88,7 @@ namespace uniset
\section sec_LogDB_DB LogDB: Работа с БД \section sec_LogDB_DB LogDB: Работа с БД
Для оптимизации, запись в БД сделана не по каждому сообщению, а через промежуточнй буфер. Для оптимизации, запись в БД сделана не по каждому сообщению, а через промежуточный буфер.
Т.е. только после того как в буфере скапливается \a qbufSize сообщений (строк) буфер скидывается в базу. Т.е. только после того как в буфере скапливается \a qbufSize сообщений (строк) буфер скидывается в базу.
Помимо этого, встроен механизм "ротации БД". Если задан параметр maxRecords (--prefix-db-max-records), Помимо этого, встроен механизм "ротации БД". Если задан параметр maxRecords (--prefix-db-max-records),
то в БД будет поддерживаться ограниченное количество записей. При этом введён "гистерезис", то в БД будет поддерживаться ограниченное количество записей. При этом введён "гистерезис",
...@@ -137,7 +137,7 @@ namespace uniset ...@@ -137,7 +137,7 @@ namespace uniset
\section sec_LogDB_DETAIL LogDB: Технические детали \section sec_LogDB_DETAIL LogDB: Технические детали
Вся релизация построена на "однопоточном" eventloop. В нём происходит, Вся реализация построена на "однопоточном" eventloop. В нём происходит,
чтение данных от логсерверов, посылка сообщений в websockets, запись в БД. чтение данных от логсерверов, посылка сообщений в websockets, запись в БД.
При этом обработка запросов REST API реализуется отдельными потоками контролируемыми libpoco. При этом обработка запросов REST API реализуется отдельными потоками контролируемыми libpoco.
......
...@@ -102,7 +102,7 @@ ...@@ -102,7 +102,7 @@
В текущей реализации в качестве датчиков разрешено использовать только типы DO или DI. В текущей реализации в качестве датчиков разрешено использовать только типы DO или DI.
\note Следует иметь ввиду, что схема \b не \b обязательно должна быть \b "СВЯЗАННОЙ" \note Следует иметь ввиду, что схема \b не \b обязательно должна быть \b "СВЯЗАННОЙ"
(все элементы связанны между собой). В файле может содержаться несколько схем внтури тэга \b <Schema>. (все элементы связанны между собой). В файле может содержаться несколько схем внутри тэга \b <Schema>.
Логика исполняется в порядке следования в файле, сверху вниз (в порядке считывания из файла). Логика исполняется в порядке следования в файле, сверху вниз (в порядке считывания из файла).
*/ */
// -------------------------------------------------------------------------- // --------------------------------------------------------------------------
......
...@@ -274,7 +274,7 @@ void PassiveLProcessor::help_print( int argc, const char* const* argv ) ...@@ -274,7 +274,7 @@ void PassiveLProcessor::help_print( int argc, const char* const* argv )
cout << "--prefix-confnode cnode - Возможность задать настроечный узел в configure.xml. По умолчанию: name" << endl; cout << "--prefix-confnode cnode - Возможность задать настроечный узел в configure.xml. По умолчанию: name" << endl;
cout << endl; cout << endl;
cout << "--prefix-schema file - Файл с логической схемой." << endl; cout << "--prefix-schema file - Файл с логической схемой." << endl;
cout << "--prefix-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-дачиком." << endl; cout << "--prefix-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-датчиком." << endl;
cout << "--prefix-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl; cout << "--prefix-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl;
} }
......
...@@ -133,7 +133,7 @@ namespace uniset ...@@ -133,7 +133,7 @@ namespace uniset
std::shared_ptr<Element> findOut(const std::string& name); std::shared_ptr<Element> findOut(const std::string& name);
// ----------------------------------------------- // -----------------------------------------------
// внутренее соединения // внутреннее соединения
// между элементами // между элементами
struct INLink struct INLink
{ {
...@@ -171,7 +171,7 @@ namespace uniset ...@@ -171,7 +171,7 @@ namespace uniset
}; };
protected: protected:
ElementMap emap; // список элеметов ElementMap emap; // список элементов
InternalList inLinks; InternalList inLinks;
ExternalList extLinks; ExternalList extLinks;
OutputsList outList; OutputsList outList;
......
...@@ -100,7 +100,7 @@ namespace uniset ...@@ -100,7 +100,7 @@ namespace uniset
- \b %rmin - минимальное значение диапазона (range min) - \b %rmin - минимальное значение диапазона (range min)
- \b %rmax - максимальное значение диапазона (range max) - \b %rmax - максимальное значение диапазона (range max)
\note Если заданные "одиночные" значения совпадают с диапазоном, то будет сгенерировано несколько сообщений. Т.е. диапазоны могут пересекатся. \note Если заданные "одиночные" значения совпадают с диапазоном, то будет сгенерировано несколько сообщений. Т.е. диапазоны могут пересекаться.
*/ */
class MQTTPublisher: class MQTTPublisher:
......
...@@ -261,8 +261,8 @@ namespace uniset ...@@ -261,8 +261,8 @@ namespace uniset
cout << "--prefix-recv-timeout msec - Таймаут на приём одного сообщения" << endl; cout << "--prefix-recv-timeout msec - Таймаут на приём одного сообщения" << endl;
cout << "--prefix-timeout msec - Таймаут для определения отсутствия соединения" << endl; cout << "--prefix-timeout msec - Таймаут для определения отсутствия соединения" << endl;
cout << "--prefix-aftersend-pause msec - Пауза после посылки запроса (каждого). По умолчанию: 0." << endl; cout << "--prefix-aftersend-pause msec - Пауза после посылки запроса (каждого). По умолчанию: 0." << endl;
cout << "--prefix-reopen-timeout msec - Таймаут для 'переоткрытия соединения' при отсутсвия соединения msec милисекунд. По умолчанию 10 сек." << endl; cout << "--prefix-reopen-timeout msec - Таймаут для 'переоткрытия соединения' при отсутствия соединения msec милисекунд. По умолчанию 10 сек." << endl;
cout << "--prefix-heartbeat-id name - Данный процесс связан с указанным аналоговым heartbeat-дачиком." << endl; cout << "--prefix-heartbeat-id name - Данный процесс связан с указанным аналоговым heartbeat-датчиком." << endl;
cout << "--prefix-heartbeat-max val - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl; cout << "--prefix-heartbeat-max val - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl;
cout << "--prefix-ready-timeout msec - Время ожидания готовности SM к работе, мсек. (-1 - ждать 'вечно')" << endl; cout << "--prefix-ready-timeout msec - Время ожидания готовности SM к работе, мсек. (-1 - ждать 'вечно')" << endl;
cout << "--prefix-force 0,1 - Сохранять значения в SM на каждом шаге, независимо от, того менялось ли значение" << endl; cout << "--prefix-force 0,1 - Сохранять значения в SM на каждом шаге, независимо от, того менялось ли значение" << endl;
...@@ -2569,7 +2569,7 @@ namespace uniset ...@@ -2569,7 +2569,7 @@ namespace uniset
} }
/*! приоритет опроса: /*! приоритет опроса:
* 1...n - задаёт "часоту" опроса. Т.е. каждые 1...n циклов * 1...n - задаёт "частоту" опроса. Т.е. каждые 1...n циклов
*/ */
size_t pollfactor = IOBase::initIntProp(it, "pollfactor", prop_prefix, false, 0); size_t pollfactor = IOBase::initIntProp(it, "pollfactor", prop_prefix, false, 0);
......
...@@ -162,7 +162,7 @@ namespace uniset ...@@ -162,7 +162,7 @@ namespace uniset
RegMap::iterator rit; RegMap::iterator rit;
// начальная инициалиазция для "записываемых" регистров // начальная инициализация для "записываемых" регистров
// Механизм: // Механизм:
// Если tcp_preinit="1", то сперва будет сделано чтение значения из устройства. // Если tcp_preinit="1", то сперва будет сделано чтение значения из устройства.
// при этом флаг mb_init=false пока не пройдёт успешной инициализации // при этом флаг mb_init=false пока не пройдёт успешной инициализации
...@@ -206,7 +206,7 @@ namespace uniset ...@@ -206,7 +206,7 @@ namespace uniset
// safe mode // safe mode
long safeMode = { safeNone }; /*!< режим безопасного состояния см. SafeMode */ long safeMode = { safeNone }; /*!< режим безопасного состояния см. SafeMode */
uniset::ObjectId safemode_id = { uniset::DefaultObjectId }; /*!< иденидентификатор для датчика безопасного режима */ uniset::ObjectId safemode_id = { uniset::DefaultObjectId }; /*!< идентификатор для датчика безопасного режима */
IOController::IOStateList::iterator safemode_it; IOController::IOStateList::iterator safemode_it;
long safemode_value = { 1 }; long safemode_value = { 1 };
...@@ -340,7 +340,7 @@ namespace uniset ...@@ -340,7 +340,7 @@ namespace uniset
bool force = { false }; /*!< флаг означающий, что надо сохранять в SM, даже если значение не менялось */ bool force = { false }; /*!< флаг означающий, что надо сохранять в SM, даже если значение не менялось */
bool force_out = { false }; /*!< флаг означающий, принудительного чтения выходов */ bool force_out = { false }; /*!< флаг означающий, принудительного чтения выходов */
bool mbregFromID = { false }; bool mbregFromID = { false };
timeout_t polltime = { 100 }; /*!< переодичность обновления данных, [мсек] */ timeout_t polltime = { 100 }; /*!< периодичность обновления данных, [мсек] */
timeout_t sleepPause_msec = { 10 }; timeout_t sleepPause_msec = { 10 };
size_t maxQueryCount = { ModbusRTU::MAXDATALEN }; /*!< максимальное количество регистров для одного запроса */ size_t maxQueryCount = { ModbusRTU::MAXDATALEN }; /*!< максимальное количество регистров для одного запроса */
...@@ -350,7 +350,7 @@ namespace uniset ...@@ -350,7 +350,7 @@ namespace uniset
IOController::IOStateList::iterator itHeartBeat; IOController::IOStateList::iterator itHeartBeat;
uniset::ObjectId test_id = { uniset::DefaultObjectId }; uniset::ObjectId test_id = { uniset::DefaultObjectId };
uniset::ObjectId sidExchangeMode = { uniset::DefaultObjectId }; /*!< иденидентификатор для датчика режима работы */ uniset::ObjectId sidExchangeMode = { uniset::DefaultObjectId }; /*!< идентификатор для датчика режима работы */
IOController::IOStateList::iterator itExchangeMode; IOController::IOStateList::iterator itExchangeMode;
long exchangeMode = { emNone }; /*!< режим работы см. ExchangeMode */ long exchangeMode = { emNone }; /*!< режим работы см. ExchangeMode */
......
...@@ -87,7 +87,7 @@ namespace uniset ...@@ -87,7 +87,7 @@ namespace uniset
\b --xxx-recv-timeout или \b recv_timeout msec - таймаут на приём одного сообщения. По умолчанию 100 мсек. \b --xxx-recv-timeout или \b recv_timeout msec - таймаут на приём одного сообщения. По умолчанию 100 мсек.
\b --xxx-timeout или \b timeout msec - таймаут на определение отсутсвия связи \b --xxx-timeout или \b timeout msec - таймаут на определение отсутствия связи
(после этого идёт попытка реинициализировать соединение) (после этого идёт попытка реинициализировать соединение)
По умолчанию 5000 мсек. По умолчанию 5000 мсек.
...@@ -176,7 +176,7 @@ namespace uniset ...@@ -176,7 +176,7 @@ namespace uniset
- \b tcp_nbyte - [1|2] номер байта. Используется если tcp_vtype="byte". - \b tcp_nbyte - [1|2] номер байта. Используется если tcp_vtype="byte".
- \b tcp_mboffset - "сдвиг"(может быть отрицательным) при опросе/записи. - \b tcp_mboffset - "сдвиг"(может быть отрицательным) при опросе/записи.
Т.е. фактически будет опрошен/записан регистр "mbreg+mboffset". Т.е. фактически будет опрошен/записан регистр "mbreg+mboffset".
- \b tcp_pollfactor - [0...n] Частота опроса. n задаёт "часоту" опроса. т.е. опрос каждые 1...n циклов - \b tcp_pollfactor - [0...n] Частота опроса. n задаёт "частоту" опроса. т.е. опрос каждые 1...n циклов
Для инициализации "выходов" (регистров которые пишутся) можно использовать поля: Для инициализации "выходов" (регистров которые пишутся) можно использовать поля:
- \b tcp_preinit - [0|1] считать регистр перед использованием (при запуске процесса) - \b tcp_preinit - [0|1] считать регистр перед использованием (при запуске процесса)
......
...@@ -89,7 +89,7 @@ namespace uniset ...@@ -89,7 +89,7 @@ namespace uniset
- \b priority - приоритет канала (чем больше число, тем выше приоритет) - \b priority - приоритет канала (чем больше число, тем выше приоритет)
- \b respond_invert - инвертировать датчик связи (DI) - \b respond_invert - инвертировать датчик связи (DI)
- \b force [1,0] - "1" - обновлять значение датчика связи в SM принудительно на каждом цикле проверки ("0" - только по изменению). - \b force [1,0] - "1" - обновлять значение датчика связи в SM принудительно на каждом цикле проверки ("0" - только по изменению).
- \b timeout - таймаут на определение отсутсвия связи для данного канала. По умолчанию берётся глобальный. - \b timeout - таймаут на определение отсутствия связи для данного канала. По умолчанию берётся глобальный.
- \b checkFunc - Номер функции для проверки соединения - \b checkFunc - Номер функции для проверки соединения
- \b checkAddr - Адрес устройства для проверки соединения - \b checkAddr - Адрес устройства для проверки соединения
- \b checkReg - Регистр для проверки соединения - \b checkReg - Регистр для проверки соединения
...@@ -110,7 +110,7 @@ namespace uniset ...@@ -110,7 +110,7 @@ namespace uniset
\b --xxx-recv-timeout или \b recv_timeout msec - таймаут на приём одного сообщения. По умолчанию 100 мсек. \b --xxx-recv-timeout или \b recv_timeout msec - таймаут на приём одного сообщения. По умолчанию 100 мсек.
\b --xxx-timeout или \b timeout msec - таймаут на определение отсутсвия связи \b --xxx-timeout или \b timeout msec - таймаут на определение отсутствия связи
(после этого идёт попытка реинициализировать соединение) (после этого идёт попытка реинициализировать соединение)
По умолчанию 5000 мсек. По умолчанию 5000 мсек.
...@@ -207,7 +207,7 @@ namespace uniset ...@@ -207,7 +207,7 @@ namespace uniset
- \b tcp_nbyte - [1|2] номер байта. Используется если tcp_vtype="byte". - \b tcp_nbyte - [1|2] номер байта. Используется если tcp_vtype="byte".
- \b tcp_mboffset - "сдвиг"(может быть отрицательным) при опросе/записи. - \b tcp_mboffset - "сдвиг"(может быть отрицательным) при опросе/записи.
Т.е. фактически будет опрошен/записан регистр "mbreg+mboffset". Т.е. фактически будет опрошен/записан регистр "mbreg+mboffset".
- \b tcp_pollfactor - [0...n] Частота опроса. n задаёт "часоту" опроса. т.е. опрос каждые 1...n циклов (зависит от общего polltime) - \b tcp_pollfactor - [0...n] Частота опроса. n задаёт "частоту" опроса. т.е. опрос каждые 1...n циклов (зависит от общего polltime)
Для инициализации "выходов" (регистров которые пишутся) можно использовать поля: Для инициализации "выходов" (регистров которые пишутся) можно использовать поля:
- \b tcp_preinit - [0|1] считать регистр перед использованием (при запуске процесса) - \b tcp_preinit - [0|1] считать регистр перед использованием (при запуске процесса)
...@@ -262,12 +262,12 @@ namespace uniset ...@@ -262,12 +262,12 @@ namespace uniset
соединения будет взят первый попавшийся регистр из списка обмена. соединения будет взят первый попавшийся регистр из списка обмена.
\warning Способ проверки при помощи "modbus-запроса" имеет ряд проблем: Если фактически производится \warning Способ проверки при помощи "modbus-запроса" имеет ряд проблем: Если фактически производится
обмен с несколькими устройствами (несколько mbaddr) через TCP-шлюз, то может быть "ложное" срабатвание, обмен с несколькими устройствами (несколько mbaddr) через TCP-шлюз, то может быть "ложное" срабатывание,
т.к. фактически состояние канала будет определяться только под связи с каким-то одним конкретным устройством. т.к. фактически состояние канала будет определяться только под связи с каким-то одним конкретным устройством.
И получается, что если обмен ведётся например с тремя устройствами, но И получается, что если обмен ведётся например с тремя устройствами, но
проверка канала происходит только по связи с первым, то если оно перестанет отвечать, это будет считаться проверка канала происходит только по связи с первым, то если оно перестанет отвечать, это будет считаться
сбоем всего канала и этот канал будет исключён из обмена (!). Если ведётся обмен только с одним устройством, сбоем всего канала и этот канал будет исключён из обмена (!). Если ведётся обмен только с одним устройством,
такой проблеммы не возникает. такой проблемы не возникает.
Но к плюсам данного способа проверки связи ("modbus-запросом") является то, что соедиенение поддерживается Но к плюсам данного способа проверки связи ("modbus-запросом") является то, что соедиенение поддерживается
постоянным, в отличие от "первого способа" при котором оно создаётся и сразу рвётся и если проверка постоянным, в отличие от "первого способа" при котором оно создаётся и сразу рвётся и если проверка
настроена достаточно часто ( < TIME_WAIT для сокетов), то при длительной работе могут закончится дескрипторы настроена достаточно часто ( < TIME_WAIT для сокетов), то при длительной работе могут закончится дескрипторы
......
...@@ -1547,7 +1547,7 @@ namespace uniset ...@@ -1547,7 +1547,7 @@ namespace uniset
cout << "--prefix-reg-from-id 0,1 - Использовать в качестве регистра sensor ID" << endl; cout << "--prefix-reg-from-id 0,1 - Использовать в качестве регистра sensor ID" << endl;
cout << "--prefix-filter-field name - Считывать список опрашиваемых датчиков, только у которых есть поле field" << endl; cout << "--prefix-filter-field name - Считывать список опрашиваемых датчиков, только у которых есть поле field" << endl;
cout << "--prefix-filter-value val - Считывать список опрашиваемых датчиков, только у которых field=value" << endl; cout << "--prefix-filter-value val - Считывать список опрашиваемых датчиков, только у которых field=value" << endl;
cout << "--prefix-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-дачиком." << endl; cout << "--prefix-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-датчиком." << endl;
cout << "--prefix-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl; cout << "--prefix-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl;
cout << "--prefix-initPause - Задержка перед инициализацией (время на активизация процесса)" << endl; cout << "--prefix-initPause - Задержка перед инициализацией (время на активизация процесса)" << endl;
cout << "--prefix-force 1 - Читать данные из SM каждый раз, а не по изменению." << endl; cout << "--prefix-force 1 - Читать данные из SM каждый раз, а не по изменению." << endl;
......
...@@ -145,7 +145,7 @@ namespace uniset ...@@ -145,7 +145,7 @@ namespace uniset
\b --xxx-default-mbaddr addr1 - slave-адрес по умолчанию для данного устройства. Если указан адрес 255 - ответ будет на любые сообщения. \b --xxx-default-mbaddr addr1 - slave-адрес по умолчанию для данного устройства. Если указан адрес 255 - ответ будет на любые сообщения.
\b --xxx-timeout или \b timeout msec - таймаут на определение отсутсвия связи. \b --xxx-timeout или \b timeout msec - таймаут на определение отсутствия связи.
\b --xxx-reply-timeout msec - таймаут на формирование ответа. \b --xxx-reply-timeout msec - таймаут на формирование ответа.
...@@ -363,7 +363,7 @@ namespace uniset ...@@ -363,7 +363,7 @@ namespace uniset
AccessMode amode; AccessMode amode;
VTypes::VType vtype; /*!< type of value */ VTypes::VType vtype; /*!< type of value */
size_t wnum; /*!< номер слова (для типов с размеров больше 2х байт */ size_t wnum; /*!< номер слова (для типов с размеров больше 2х байт */
size_t nbyte; /*!< номер байта, который надо "сохранить" из "пришедщего в запросе" слова. [1-2] */ size_t nbyte; /*!< номер байта, который надо "сохранить" из "пришедшего в запросе" слова. [1-2] */
std::shared_ptr<BitRegProperty> bitreg; /*!< указатель, как признак является ли данный регистр "сборным" из битовых */ std::shared_ptr<BitRegProperty> bitreg; /*!< указатель, как признак является ли данный регистр "сборным" из битовых */
ModbusRTU::RegID regID; ModbusRTU::RegID regID;
...@@ -473,7 +473,7 @@ namespace uniset ...@@ -473,7 +473,7 @@ namespace uniset
ModbusRTU::mbErrCode read4314( ModbusRTU::MEIMessageRDI& query, ModbusRTU::mbErrCode read4314( ModbusRTU::MEIMessageRDI& query,
ModbusRTU::MEIMessageRetRDI& reply ); ModbusRTU::MEIMessageRetRDI& reply );
// т.к. в функциях (much_real_read,nuch_real_write) рассчёт на отсортированность IOMap // т.к. в функциях (much_real_read,nuch_real_write) расчёт на отсортированность IOMap
// то использовать unordered_map нельзя // то использовать unordered_map нельзя
typedef std::map<ModbusRTU::RegID, IOProperty> RegMap; typedef std::map<ModbusRTU::RegID, IOProperty> RegMap;
......
...@@ -972,7 +972,7 @@ namespace uniset ...@@ -972,7 +972,7 @@ namespace uniset
try try
{ {
#if 1 #if 1
// Вариант через setValue...(заодно внтури проверяются пороги) // Вариант через setValue...(заодно внутри проверяются пороги)
setValue(ii.si.id, ii.value, getId()); setValue(ii.si.id, ii.value, getId());
#else #else
......
...@@ -40,7 +40,7 @@ namespace uniset ...@@ -40,7 +40,7 @@ namespace uniset
{ {
// ----------------------------------------------------------------------------- // -----------------------------------------------------------------------------
/*! \page page_SharedMemory Реализация разделямой между процессами памяти (SharedMemory) /*! \page page_SharedMemory Реализация разделяемой между процессами памяти (SharedMemory)
\section sec_SM_Common Задачи решаемые объектом SharedMemory \section sec_SM_Common Задачи решаемые объектом SharedMemory
...@@ -121,14 +121,14 @@ namespace uniset ...@@ -121,14 +121,14 @@ namespace uniset
\section sec_SM_Event Уведомление о рестарте SM \section sec_SM_Event Уведомление о рестарте SM
В SM реализован механизм позволяющий задавать список объетов, В SM реализован механизм позволяющий задавать список объектов,
которым присылается уведомление о старте/рестарте SM. которым присылается уведомление о старте/рестарте SM.
Параметр определяющий фильтр, по которому формируется список объектов Параметр определяющий фильтр, по которому формируется список объектов
задаётся из командной строки \b --e-filter. задаётся из командной строки \b --e-filter.
Параметр \b --e-startup-pause msec - задаёт паузу после старта SM, Параметр \b --e-startup-pause msec - задаёт паузу после старта SM,
после которой заданным объектам посылается уведомление. после которой заданным объектам посылается уведомление.
Чтобы указать объект которому необходимо присылать уведомление, Чтобы указать объект которому необходимо присылать уведомление,
необходимо для него в конфигурайионном файле указать поле необходимо для него в конфигурационном файле указать поле
\b evnt_xxx="1", где \b xxx - имя заданное в качестве параметра \b evnt_xxx="1", где \b xxx - имя заданное в качестве параметра
\b --e-filter. \b --e-filter.
Пример: Пример:
...@@ -145,7 +145,7 @@ namespace uniset ...@@ -145,7 +145,7 @@ namespace uniset
\section sec_SM_Depends Механизм зависимостей между датчиками \section sec_SM_Depends Механизм зависимостей между датчиками
В SM реализован механизм позволяющий задавать зависимости между датчиками. Т.е. датчик В SM реализован механизм позволяющий задавать зависимости между датчиками. Т.е. датчик
будет равен "0" пока разрешающий датчик не будет равено "1". Ниже показан пример конфигурирования будет равен "0" пока разрешающий датчик не будет равно "1". Ниже показан пример конфигурирования
зависимости. зависимости.
\code \code
<item id="20050" iotype="AI" name="Sensor1"" textname="Зависящий датчик 1"> <item id="20050" iotype="AI" name="Sensor1"" textname="Зависящий датчик 1">
...@@ -178,8 +178,8 @@ namespace uniset ...@@ -178,8 +178,8 @@ namespace uniset
аналоговый(счётчик) и дискретный. Во время работы, процесс периодически (время задаётся в настройках) аналоговый(счётчик) и дискретный. Во время работы, процесс периодически (время задаётся в настройках)
сохраняет в свой \b аналоговый датчик заданное значение (количество тактов). сохраняет в свой \b аналоговый датчик заданное значение (количество тактов).
В свою очередь процесс SM, каждый "такт"(время между шагами задаётся в настройках), В свою очередь процесс SM, каждый "такт"(время между шагами задаётся в настройках),
"отнимает" у этого значения 1 (декриментирует). Пока значение счётчика больше нуля, дискретный датчик "отнимает" у этого значения 1 (декрементирует). Пока значение счётчика больше нуля, дискретный датчик
держиться равным "1" (т.е. 1 - процесс "жив"). Если процесс "вылетает" и перестаёт обновлять свой счётчик, держится равным "1" (т.е. 1 - процесс "жив"). Если процесс "вылетает" и перестаёт обновлять свой счётчик,
то через некоторое количество тактов его счётчик становится меньше нуля. Как только это происходит, SM фиксирует, то через некоторое количество тактов его счётчик становится меньше нуля. Как только это происходит, SM фиксирует,
"недоступность" процесса, и выставляет дискретный датчик в ноль (т.е. 0 - процесс вылетел(недоступен)). "недоступность" процесса, и выставляет дискретный датчик в ноль (т.е. 0 - процесс вылетел(недоступен)).
...@@ -188,14 +188,14 @@ namespace uniset ...@@ -188,14 +188,14 @@ namespace uniset
и за заданное время процесс не перезапустился (не обновил свой счётчик), происходит и за заданное время процесс не перезапустился (не обновил свой счётчик), происходит
перезагрузка контроллера (SM перестаёт сбрасывать WDT-таймер). перезагрузка контроллера (SM перестаёт сбрасывать WDT-таймер).
У аналоговых датчиков "сердцебиения" в конфигурайионном файле необходимо указывать \b heartbeat="1". У аналоговых датчиков "сердцебиения" в конфигурационном файле необходимо указывать \b heartbeat="1".
А также поля: А также поля:
<br>\b heartbeat_ds_name - имя дискретного датчика, связанного с данным аналоговым <br>\b heartbeat_ds_name - имя дискретного датчика, связанного с данным аналоговым
<br>\b heartbeat_node="ses" - фильтрующее поле (см. --heartbeat-node) <br>\b heartbeat_node="ses" - фильтрующее поле (см. --heartbeat-node)
<br>\b heartbeat_reboot_msec - время ожидания перезапуска процесса. Это необязательный параметр, задаётся только в случае <br>\b heartbeat_reboot_msec - время ожидания перезапуска процесса. Это необязательный параметр, задаётся только в случае
необходимости перезапуска контроллера. необходимости перезапуска контроллера.
Пример задания датчиков "сердцебияния": Пример задания датчиков "сердцебиения":
<br>_31_04_AS - аналоговый (счётчик) <br>_31_04_AS - аналоговый (счётчик)
<br>_41_04_S - дискретный ("доступность процесса") <br>_41_04_S - дискретный ("доступность процесса")
...@@ -241,8 +241,8 @@ namespace uniset ...@@ -241,8 +241,8 @@ namespace uniset
id - задаёт (внутренний) идентификатор "истории" id - задаёт (внутренний) идентификатор "истории"
fuse_id - идентификатор датчика "детонатора" fuse_id - идентификатор датчика "детонатора"
fuse_value - значение срабатывания (для аналогового "детонатора") fuse_value - значение срабатывания (для аналогового "детонатора")
fuse_invert - ивертировать (для дискретных "детонаторов"). fuse_invert - инвертировать (для дискретных "детонаторов").
Т.е. срабатвание на значение "0". Т.е. срабатывание на значение "0".
size - количество точек в хранимой истории size - количество точек в хранимой истории
filter - поле используемое в качестве фильтра, определяющего датчики filter - поле используемое в качестве фильтра, определяющего датчики
...@@ -251,7 +251,7 @@ namespace uniset ...@@ -251,7 +251,7 @@ namespace uniset
Каждый датчик может входить в любое количество групп (историй). Каждый датчик может входить в любое количество групп (историй).
Механизм фукнционирует по следующей логике: Механизм функционирует по следующей логике:
При запуске происходит считывание параметров секции <History> При запуске происходит считывание параметров секции <History>
и заполнение соответствующих структур хранения. При этом происходит и заполнение соответствующих структур хранения. При этом происходит
...@@ -263,8 +263,8 @@ namespace uniset ...@@ -263,8 +263,8 @@ namespace uniset
а одно устаревшее удаляется, тем самым всегда поддерживается буфер не более а одно устаревшее удаляется, тем самым всегда поддерживается буфер не более
\b size точек. \b size точек.
Помимо этого в фукнцииях изменения датчиков (семейство setValue) отслеживается Помимо этого в функциях изменения датчиков (семейство setValue) отслеживается
изменение состояния "детонаторов". Если срабатывает заданое условие для изменение состояния "детонаторов". Если срабатывает заданное условие для
"сброса" дампа, инициируется сигнал, в который передаётся идентификатор истории "сброса" дампа, инициируется сигнал, в который передаётся идентификатор истории
и текущая накопленная история. и текущая накопленная история.
...@@ -402,7 +402,7 @@ namespace uniset ...@@ -402,7 +402,7 @@ namespace uniset
typedef std::list<HistoryInfo> History; typedef std::list<HistoryInfo> History;
// т.к. могуть быть одинаковые "детонаторы" для разных "историй" то, // т.к. могут быть одинаковые "детонаторы" для разных "историй" то,
// вводим не просто map, а "map списка историй". // вводим не просто map, а "map списка историй".
// точнее итераторов-историй. // точнее итераторов-историй.
typedef std::list<History::iterator> HistoryItList; typedef std::list<History::iterator> HistoryItList;
......
...@@ -27,7 +27,7 @@ namespace uniset ...@@ -27,7 +27,7 @@ namespace uniset
// ----------------------------------------------------------------------------- // -----------------------------------------------------------------------------
namespace UniSetUDP namespace UniSetUDP
{ {
/*! Для оптимизации размера передаваемх данных, но с учётом того, что ID могут идти не подряд. /*! Для оптимизации размера передаваемых данных, но с учётом того, что ID могут идти не подряд.
Сделан следующий формат: Сделан следующий формат:
Для аналоговых величин передаётся массив пар "id-value"(UDPAData). Для аналоговых величин передаётся массив пар "id-value"(UDPAData).
Для булевых величин - отдельно массив ID и отдельно битовый массив со значениями, Для булевых величин - отдельно массив ID и отдельно битовый массив со значениями,
...@@ -41,7 +41,7 @@ namespace uniset ...@@ -41,7 +41,7 @@ namespace uniset
"ByteOrder" "ByteOrder"
============ ============
В текущей версии протокола. В UDPHeader содержиться информации о порядке байт. В текущей версии протокола. В UDPHeader содержится информации о порядке байт.
Поэтому логика следующая: Поэтому логика следующая:
- Узел который посылает, ничего не перекодирует и просто посылает данные так как хранит - Узел который посылает, ничего не перекодирует и просто посылает данные так как хранит
(информация о порядке байт, если специально не выставить, будет выставлена при компиляции, см. конструктор) (информация о порядке байт, если специально не выставить, будет выставлена при компиляции, см. конструктор)
......
...@@ -92,7 +92,7 @@ namespace uniset ...@@ -92,7 +92,7 @@ namespace uniset
--prefix-nodes-confnode name. По умолчанию настройка ведётся по секции <nodes> --prefix-nodes-confnode name. По умолчанию настройка ведётся по секции <nodes>
\section pgUNetUDP_Reserv Настройка резервного канала связи \section pgUNetUDP_Reserv Настройка резервного канала связи
В текущей реализации поддерживается возможность обмена по двум подсетям (эзернет-каналам). В текущей реализации поддерживается возможность обмена по двум подсетям (Ethernet-каналам).
Она основана на том, что, для каждого узла помимо основного "читателя", Она основана на том, что, для каждого узла помимо основного "читателя",
создаётся дополнительный "читатель"(поток) слушающий другой ip-адрес и порт. создаётся дополнительный "читатель"(поток) слушающий другой ip-адрес и порт.
А так же, для локального узла создаётся дополнительный "писатель"(поток), А так же, для локального узла создаётся дополнительный "писатель"(поток),
...@@ -119,7 +119,7 @@ namespace uniset ...@@ -119,7 +119,7 @@ namespace uniset
для каждого датчика. Суть механизма заключается в том, что для каждого датчика можно задать свойство для каждого датчика. Суть механизма заключается в том, что для каждого датчика можно задать свойство
- \b prefix_sendfactor="N" Где N>1 - задаёт "делитель" относительно \b sendpause определяющий с какой частотой - \b prefix_sendfactor="N" Где N>1 - задаёт "делитель" относительно \b sendpause определяющий с какой частотой
информация о данном датчике будет посылаться. Например N=2 - каждый второй цикл, N=3 - каждый третий и т.п. информация о данном датчике будет посылаться. Например N=2 - каждый второй цикл, N=3 - каждый третий и т.п.
При загрузке все датчики (относщиеся к данному процессу) разбиваются на группы пакетов согласно своей частоте посылки. При загрузке все датчики (относящиеся к данному процессу) разбиваются на группы пакетов согласно своей частоте посылки.
При этом внутри одной группы датчики разбиваются по пакетам согласно заданному максимальному размеру пакета При этом внутри одной группы датчики разбиваются по пакетам согласно заданному максимальному размеру пакета
(см. конструктор класса UNetSender()). (см. конструктор класса UNetSender()).
......
...@@ -40,7 +40,7 @@ namespace uniset ...@@ -40,7 +40,7 @@ namespace uniset
* =============== * ===============
* Собственно реализация сделана так: * Собственно реализация сделана так:
* В данных передаётся номер пакета. На случай если несколько пакетов придут не в той последовательности * В данных передаётся номер пакета. На случай если несколько пакетов придут не в той последовательности
* что были посланы, сделана очередь с приоритетом. В качестве приориета используется номер пакета * что были посланы, сделана очередь с приоритетом. В качестве приоритета используется номер пакета
* (чем меньше тем старше). При этом обработка ведётся только тех пакетов, которые идут "подряд", * (чем меньше тем старше). При этом обработка ведётся только тех пакетов, которые идут "подряд",
* как только встречается "дырка" происходит ожидание её "заполения". Если в течение времени (lostTimeout) * как только встречается "дырка" происходит ожидание её "заполения". Если в течение времени (lostTimeout)
* "дырка" не исчезает, увеличивается счётчик потерянных пакетов и обработка продолжается дальше.. * "дырка" не исчезает, увеличивается счётчик потерянных пакетов и обработка продолжается дальше..
...@@ -60,12 +60,12 @@ namespace uniset ...@@ -60,12 +60,12 @@ namespace uniset
* Т.к. в общем случае, данные могут быть разбиты не несколько (много) пакетов, то для каждого из них выделен свой кэш и создан отдельный * Т.к. в общем случае, данные могут быть разбиты не несколько (много) пакетов, то для каждого из них выделен свой кэш и создан отдельный
* map, ключом в котором является идентификатор данных (см. UDPMessage::getDataID()). * map, ключом в котором является идентификатор данных (см. UDPMessage::getDataID()).
* Кэш в map добавляется когда приходит пакет с новым UDPMessage::getDataID() и в дальнейшим используется для этого пакета. * Кэш в map добавляется когда приходит пакет с новым UDPMessage::getDataID() и в дальнейшим используется для этого пакета.
* В текущей реализации размер map не контролируется (завязан на UDPMessage::getDataID()) и расчитан на статичность пакетов, * В текущей реализации размер map не контролируется (завязан на UDPMessage::getDataID()) и рассчитан на статичность пакетов,
* т.е. на то что UNetSender не будет с течением времени менять структуру отправляемых пакетов. * т.е. на то что UNetSender не будет с течением времени менять структуру отправляемых пакетов.
* *
* Обработка сбоя или переполнения счётчика пакетов(перехода через максимум) * Обработка сбоя или переполнения счётчика пакетов(перехода через максимум)
* ========================================================================= * =========================================================================
* Для защиты от сбоя счётика сделана следующая логика: * Для защиты от сбоя счётчика сделана следующая логика:
* Если номер очередного пришедшего пакета отличается от последнего обработанного на maxDifferens, то считается, * Если номер очередного пришедшего пакета отличается от последнего обработанного на maxDifferens, то считается,
* что произошёл сбой счётчика и происходит ожидание пока функция update, не обработает основную очередь полностью. * что произошёл сбой счётчика и происходит ожидание пока функция update, не обработает основную очередь полностью.
* При этом принимаемые пакеты складываются во временную очередь qtmp. Как только основная очередь пустеет, * При этом принимаемые пакеты складываются во временную очередь qtmp. Как только основная очередь пустеет,
...@@ -176,7 +176,7 @@ namespace uniset ...@@ -176,7 +176,7 @@ namespace uniset
void setUpdateStrategy( UpdateStrategy set ); void setUpdateStrategy( UpdateStrategy set );
// специальная обёртка, захватывающая или нет mutex в зависимости от стратегии // специальная обёртка, захватывающая или нет mutex в зависимости от стратегии
// (т.к. при evloop mutex захватытвать не нужно) // (т.к. при evloop mutex захватывать не нужно)
class pack_guard class pack_guard
{ {
public: public:
...@@ -241,8 +241,8 @@ namespace uniset ...@@ -241,8 +241,8 @@ namespace uniset
private: private:
UNetReceiver(); UNetReceiver();
timeout_t recvpause = { 10 }; /*!< пауза меджду приёмами пакетов, [мсек] */ timeout_t recvpause = { 10 }; /*!< пауза между приёмами пакетов, [мсек] */
timeout_t updatepause = { 100 }; /*!< переодичность обновления данных в SM, [мсек] */ timeout_t updatepause = { 100 }; /*!< периодичность обновления данных в SM, [мсек] */
std::unique_ptr<UDPReceiveU> udp; std::unique_ptr<UDPReceiveU> udp;
std::string addr; std::string addr;
...@@ -300,13 +300,13 @@ namespace uniset ...@@ -300,13 +300,13 @@ namespace uniset
std::mutex packMutex; /*!< mutex для работы с очередью */ std::mutex packMutex; /*!< mutex для работы с очередью */
size_t pnum = { 0 }; /*!< текущий номер обработанного сообщения, для проверки непрерывности последовательности пакетов */ size_t pnum = { 0 }; /*!< текущий номер обработанного сообщения, для проверки непрерывности последовательности пакетов */
/*! максимальная разница межд номерами пакетов, при которой считается, что счётчик пакетов /*! максимальная разница между номерами пакетов, при которой считается, что счётчик пакетов
* прошёл через максимум или сбился... * прошёл через максимум или сбился...
*/ */
size_t maxDifferens = { 20 }; size_t maxDifferens = { 20 };
PacketQueue qtmp; /*!< очередь на время обработки(очистки) основной очереди */ PacketQueue qtmp; /*!< очередь на время обработки(очистки) основной очереди */
bool waitClean = { false }; /*!< флаг означающий, что ждём очистики очереди до конца */ bool waitClean = { false }; /*!< флаг означающий, что ждём очистки очереди до конца */
size_t rnum = { 0 }; /*!< текущий номер принятого сообщения, для проверки "переполнения" или "сбоя" счётчика */ size_t rnum = { 0 }; /*!< текущий номер принятого сообщения, для проверки "переполнения" или "сбоя" счётчика */
size_t maxProcessingCount = { 100 }; /*!< максимальное число обрабатываемых за один раз сообщений */ size_t maxProcessingCount = { 100 }; /*!< максимальное число обрабатываемых за один раз сообщений */
......
...@@ -51,7 +51,7 @@ namespace uniset ...@@ -51,7 +51,7 @@ namespace uniset
* ОПТИМИЗАЦИЯ N1: Для оптимизации обработки посылаемых пакетов (на стороне UNetSender) сделана следующая логика: * ОПТИМИЗАЦИЯ N1: Для оптимизации обработки посылаемых пакетов (на стороне UNetSender) сделана следующая логика:
* Номер очередного посылаемого пакета меняется (увеличивается) только, если изменились данные с момента * Номер очередного посылаемого пакета меняется (увеличивается) только, если изменились данные с момента
последней посылки. Для этого по данным каждый раз производится расчёт UNetUDP::makeCRC() и сравнивается с последним. последней посылки. Для этого по данным каждый раз производится расчёт UNetUDP::makeCRC() и сравнивается с последним.
На стороне UNetReceiver пакаеты с повторными номерами (т.е. уже обработанные) - откидываются. На стороне UNetReceiver пакеты с повторными номерами (т.е. уже обработанные) - откидываются.
* *
* *
* Создание соединения * Создание соединения
......
...@@ -470,7 +470,7 @@ bool UniExchange::initItem( UniXML::iterator& it ) ...@@ -470,7 +470,7 @@ bool UniExchange::initItem( UniXML::iterator& it )
void UniExchange::help_print( int argc, const char** argv ) void UniExchange::help_print( int argc, const char** argv )
{ {
cout << "--unet-polltime msec - Пауза между опросами узлов. По умолчанию 200 мсек." << endl; cout << "--unet-polltime msec - Пауза между опросами узлов. По умолчанию 200 мсек." << endl;
// cout << "--unet-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-дачиком." << endl; // cout << "--unet-heartbeat-id - Данный процесс связан с указанным аналоговым heartbeat-датчиком." << endl;
// cout << "--unet-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl; // cout << "--unet-heartbeat-max - Максимальное значение heartbeat-счётчика для данного процесса. По умолчанию 10." << endl;
cout << "--unet-sm-ready-timeout - время на ожидание старта SM" << endl; cout << "--unet-sm-ready-timeout - время на ожидание старта SM" << endl;
} }
......
...@@ -106,7 +106,7 @@ namespace uniset ...@@ -106,7 +106,7 @@ namespace uniset
{ {
return minVal; return minVal;
} }
/*! Возвращает максимальное значение 'x' втретившееся в диаграмме */ /*! Возвращает максимальное значение 'x' встретившееся в диаграмме */
inline long getMaxValue() const noexcept inline long getMaxValue() const noexcept
{ {
return maxVal; return maxVal;
...@@ -154,7 +154,7 @@ namespace uniset ...@@ -154,7 +154,7 @@ namespace uniset
return rightRaw; return rightRaw;
} }
/*! построение характеристрики из конф. файла /*! построение характеристики из конф. файла
\param name - название характеристики в файле \param name - название характеристики в файле
\param confile - файл содержащий данные \param confile - файл содержащий данные
\param node - если node!=0, то используется этот узел... \param node - если node!=0, то используется этот узел...
...@@ -225,8 +225,8 @@ namespace uniset ...@@ -225,8 +225,8 @@ namespace uniset
TypeOfValue getY( const TypeOfValue& x ) const noexcept; /*!< получить значение Y */ TypeOfValue getY( const TypeOfValue& x ) const noexcept; /*!< получить значение Y */
TypeOfValue getX( const TypeOfValue& y ) const noexcept; /*!< получить значение X */ TypeOfValue getX( const TypeOfValue& y ) const noexcept; /*!< получить значение X */
TypeOfValue calcY( const TypeOfValue& x ) const noexcept; /*!< расчитать значение для x */ TypeOfValue calcY( const TypeOfValue& x ) const noexcept; /*!< рассчитать значение для x */
TypeOfValue calcX( const TypeOfValue& y ) const noexcept; /*!< расчитать значение для y */ TypeOfValue calcX( const TypeOfValue& y ) const noexcept; /*!< рассчитать значение для y */
inline bool operator < ( const Part& p ) const noexcept inline bool operator < ( const Part& p ) const noexcept
{ {
......
...@@ -95,7 +95,7 @@ namespace uniset ...@@ -95,7 +95,7 @@ namespace uniset
// Вторая ступень фильтра, математическая реализация RC фильтра // Вторая ступень фильтра, математическая реализация RC фильтра
double secondLevel( double val ); double secondLevel( double val );
double Ti; // Постоянная времени для апериодического звена в милисекундах double Ti; // Постоянная времени для апериодического звена в миллисекундах
double val; // Текущее значение второй ступени фильтра double val; // Текущее значение второй ступени фильтра
double M; // Среднее арифметическое double M; // Среднее арифметическое
double S; // Среднеквадратичное отклонение double S; // Среднеквадратичное отклонение
...@@ -107,7 +107,7 @@ namespace uniset ...@@ -107,7 +107,7 @@ namespace uniset
typedef std::vector<int> MedianVector; typedef std::vector<int> MedianVector;
MedianVector mvec; MedianVector mvec;
bool mvec_sorted; // флаг, что mvec остортирован (заполнен) bool mvec_sorted; // флаг, что mvec отсортирован (заполнен)
typedef std::vector<double> Coeff; typedef std::vector<double> Coeff;
Coeff w; // Вектор коэффициентов для filterIIR Coeff w; // Вектор коэффициентов для filterIIR
......
...@@ -183,7 +183,7 @@ namespace uniset ...@@ -183,7 +183,7 @@ namespace uniset
static bool processingAsDO( IOBase* it, const std::shared_ptr<SMInterface>& shm, bool force ); static bool processingAsDO( IOBase* it, const std::shared_ptr<SMInterface>& shm, bool force );
static void processingThreshold( IOBase* it, const std::shared_ptr<SMInterface>& shm, bool force ); static void processingThreshold( IOBase* it, const std::shared_ptr<SMInterface>& shm, bool force );
/*! \param initPrefixOnly - TRUE - инициализировать только свойста с prefix (или брать значения по умолчанию). /*! \param initPrefixOnly - TRUE - инициализировать только свойства с prefix (или брать значения по умолчанию).
FALSE - сперва искать свойство с prefix, если не найдено брать без prefix. FALSE - сперва искать свойство с prefix, если не найдено брать без prefix.
*/ */
static bool initItem( IOBase* b, UniXML::iterator& it, const std::shared_ptr<SMInterface>& shm, static bool initItem( IOBase* b, UniXML::iterator& it, const std::shared_ptr<SMInterface>& shm,
......
...@@ -56,7 +56,7 @@ namespace uniset ...@@ -56,7 +56,7 @@ namespace uniset
mtT_Str8 mtT_Str8
}; };
// ------------------------------------------------------------------------- // -------------------------------------------------------------------------
std::string type2str( MTRType t ); /*!< преоразование строки в тип */ std::string type2str( MTRType t ); /*!< преобразование строки в тип */
MTRType str2type( const std::string& s ); /*!< преобразование названия в строку */ MTRType str2type( const std::string& s ); /*!< преобразование названия в строку */
size_t wsize( MTRType t ); /*!< длина данных в словах */ size_t wsize( MTRType t ); /*!< длина данных в словах */
// ------------------------------------------------------------------------- // -------------------------------------------------------------------------
......
...@@ -27,7 +27,7 @@ namespace uniset ...@@ -27,7 +27,7 @@ namespace uniset
Формулы выведены на основе разностных уравнений Формулы выведены на основе разностных уравнений
см. http://atm.h1.ru/root/theory/theory33.html см. http://atm.h1.ru/root/theory/theory33.html
Он даёт неплохой результат и опимальнее по расчётам Он даёт неплохой результат и оптимальнее по расчётам
(содержит только умножение, не переполняется (содержит только умножение, не переполняется
т.к. учитывает только два последних шага) т.к. учитывает только два последних шага)
*/ */
......
...@@ -216,7 +216,7 @@ class UObject_SK: ...@@ -216,7 +216,7 @@ class UObject_SK:
int askPause; /*!< пауза между неудачными попытками заказать датчики */ int askPause; /*!< пауза между неудачными попытками заказать датчики */
IOController_i::SensorInfo si; IOController_i::SensorInfo si;
bool forceOut; /*!< флаг принудительного обноления "выходов" */ bool forceOut; /*!< флаг принудительного обнуления "выходов" */
std::shared_ptr<uniset::LogAgregator> loga; std::shared_ptr<uniset::LogAgregator> loga;
std::shared_ptr<DebugStream> mylog; std::shared_ptr<DebugStream> mylog;
......
...@@ -176,7 +176,7 @@ TEST_CASE("UInterface", "[UInterface]") ...@@ -176,7 +176,7 @@ TEST_CASE("UInterface", "[UInterface]")
REQUIRE_THROWS_AS( ui.askThreshold(aid, 3, UniversalIO::UIONotify, 50, 20, false, testOID), IONotifyController_i::BadRange ); REQUIRE_THROWS_AS( ui.askThreshold(aid, 3, UniversalIO::UIONotify, 50, 20, false, testOID), IONotifyController_i::BadRange );
IONotifyController_i::ThresholdsListSeq_var slist = ui.getThresholdsList(aid); IONotifyController_i::ThresholdsListSeq_var slist = ui.getThresholdsList(aid);
REQUIRE( slist->length() == 1 ); // количество датчиков с порогоами = 1 (это aid) REQUIRE( slist->length() == 1 ); // количество датчиков с порогами = 1 (это aid)
// 3 порога мы создали выше(askThreshold) + 1 который в настроечном файле в секции <thresholds> // 3 порога мы создали выше(askThreshold) + 1 который в настроечном файле в секции <thresholds>
REQUIRE( slist[0].tlist.length() == 4 ); REQUIRE( slist[0].tlist.length() == 4 );
......
...@@ -160,7 +160,7 @@ namespace uniset ...@@ -160,7 +160,7 @@ namespace uniset
/*! интерфейс к карте объектов */ /*! интерфейс к карте объектов */
std::shared_ptr<ObjectIndex> oind; std::shared_ptr<ObjectIndex> oind;
/*! интерфейс к работе с локальнымми ior-файлами */ /*! интерфейс к работе с локальными ior-файлами */
std::shared_ptr<IORFile> iorfile; std::shared_ptr<IORFile> iorfile;
/*! указатель на конфигурационный xml */ /*! указатель на конфигурационный xml */
......
...@@ -34,7 +34,7 @@ namespace uniset ...@@ -34,7 +34,7 @@ namespace uniset
\section secDBServer Сервис ведения БД \section secDBServer Сервис ведения БД
\subsection subDBS_common Общие сведения \subsection subDBS_common Общие сведения
Предназначен для работы с БД. Предназначен для работы с БД.
Основная задача это - сохрание информации о датчиках, ведение журнала сообщений. Основная задача это - сохранение информации о датчиках, ведение журнала сообщений.
\subsection subDBS_idea Сценарий работы \subsection subDBS_idea Сценарий работы
На узле, где ведётся БД запускается один экземпляр сервиса. Клиенты могут получить доступ, несколькими способами: На узле, где ведётся БД запускается один экземпляр сервиса. Клиенты могут получить доступ, несколькими способами:
......
...@@ -136,7 +136,7 @@ class DebugStream : public std::ostream ...@@ -136,7 +136,7 @@ class DebugStream : public std::ostream
return fname; return fname;
} }
// имя лог файла можно установить отдельно, но не вклчать запись.. // имя лог файла можно установить отдельно, но не включать запись..
inline void setLogFile( const std::string& n ) noexcept inline void setLogFile( const std::string& n ) noexcept
{ {
fname = n; fname = n;
......
...@@ -29,7 +29,7 @@ namespace uniset ...@@ -29,7 +29,7 @@ namespace uniset
virtual void evfinish() {} virtual void evfinish() {}
// подготовка перед запуском loop // подготовка перед запуском loop
// запусу своих ev::xxx.start() // запуску своих ev::xxx.start()
virtual void evprepare() {} virtual void evprepare() {}
// Управление потоком событий // Управление потоком событий
......
...@@ -33,7 +33,7 @@ namespace uniset ...@@ -33,7 +33,7 @@ namespace uniset
песок сыплется... если весь пересыпался - срабатывает условие 'check()==true'. песок сыплется... если весь пересыпался - срабатывает условие 'check()==true'.
Если во время работы условие изменилось (часы перевернули в обратную сторону), то Если во время работы условие изменилось (часы перевернули в обратную сторону), то
уже успевший пересыпаться песок, начинает пересыпаться в обратную сторону. Если опять уже успевший пересыпаться песок, начинает пересыпаться в обратную сторону. Если опять
повернули часы... продолжает сыпаться опять (добвляясь к тому песку, что "не успел" высыпаться обратно). повернули часы... продолжает сыпаться опять (добавляясь к тому песку, что "не успел" высыпаться обратно).
Т.е. до момента срабатывания уже меньше времени чем "полное время" и т.д. Т.е. до момента срабатывания уже меньше времени чем "полное время" и т.д.
Класс является "пассивным", т.е. требует периодического вызова функции rotate и check, Класс является "пассивным", т.е. требует периодического вызова функции rotate и check,
...@@ -42,7 +42,7 @@ namespace uniset ...@@ -42,7 +42,7 @@ namespace uniset
\par Пример использования. \par Пример использования.
Допустим у вас есть сигнал "температура"(in_temp) и вам необходимо выставить какой-то Допустим у вас есть сигнал "температура"(in_temp) и вам необходимо выставить какой-то
флаг о перегреве (isOverheating). флаг о перегреве (isOverheating).
Если температура продержиться выше порога в течение 10 секунд check() станет "true". Если температура продержится выше порога в течение 10 секунд check() станет "true".
Если температура станет меньше порога через 6 секунд ("песок начнёт обратно пересыпаться"), Если температура станет меньше порога через 6 секунд ("песок начнёт обратно пересыпаться"),
а потом опять станет выше, то до срабатывания check() == true уже останется 4 сек, а не 10 сек. а потом опять станет выше, то до срабатывания check() == true уже останется 4 сек, а не 10 сек.
Получается, что для срабатывания check()=true сигнал должен не колеблясь держаться больше заданного времени. Получается, что для срабатывания check()=true сигнал должен не колеблясь держаться больше заданного времени.
......
...@@ -72,7 +72,7 @@ namespace uniset ...@@ -72,7 +72,7 @@ namespace uniset
UniXML::iterator& it, xmlNode* sec) UniXML::iterator& it, xmlNode* sec)
uxml - интерфейс для работы с xml-файлом uxml - интерфейс для работы с xml-файлом
it - интератор(указатель) на текущий считываемый xml-узел (item) it - итератор(указатель) на текущий считываемый xml-узел (item)
sec - указатель на корневой узел секции (SubscriberList) sec - указатель на корневой узел секции (SubscriberList)
*/ */
void setReadItem( ReaderSlot sl ); void setReadItem( ReaderSlot sl );
...@@ -86,7 +86,7 @@ namespace uniset ...@@ -86,7 +86,7 @@ namespace uniset
UniXML::iterator& it, xmlNode* sec) UniXML::iterator& it, xmlNode* sec)
uxml - интерфейс для работы с xml-файлом uxml - интерфейс для работы с xml-файлом
it - интератор(указатель) на текущий считываемый xml-узел (<consumer>) it - итератор(указатель) на текущий считываемый xml-узел (<consumer>)
sec - указатель на текущий узел сообщения (<item>) sec - указатель на текущий узел сообщения (<item>)
*/ */
void setReadConsumerItem( ReaderSlot sl ); void setReadConsumerItem( ReaderSlot sl );
...@@ -118,7 +118,7 @@ namespace uniset ...@@ -118,7 +118,7 @@ namespace uniset
bool xxxMyClass::myfunc(UniXML& xml, bool xxxMyClass::myfunc(UniXML& xml,
UniXML::iterator& it, xmlNode* sec) UniXML::iterator& it, xmlNode* sec)
uxml - интерфейс для работы с xml-файлом uxml - интерфейс для работы с xml-файлом
it - интератор(указатель) на текущий считываемый xml-узел (<sensor>) it - итератор(указатель) на текущий считываемый xml-узел (<sensor>)
sec - указатель на корневой узел секции (<threshold>) sec - указатель на корневой узел секции (<threshold>)
*/ */
void setReadThresholdItem( ReaderSlot sl ); void setReadThresholdItem( ReaderSlot sl );
......
...@@ -118,7 +118,7 @@ namespace uniset ...@@ -118,7 +118,7 @@ namespace uniset
static const long not_specified_value = { std::numeric_limits<long>::max() }; static const long not_specified_value = { std::numeric_limits<long>::max() };
// ================== Достпуные сигналы ================= // ================== Доступные сигналы =================
/*! /*!
// \warning В сигнале напрямую передаётся указатель на внутреннюю структуру! // \warning В сигнале напрямую передаётся указатель на внутреннюю структуру!
// Это не очень хорошо, с точки зрения "архитектуры", но оптимальнее по быстродействию! // Это не очень хорошо, с точки зрения "архитектуры", но оптимальнее по быстродействию!
...@@ -137,7 +137,7 @@ namespace uniset ...@@ -137,7 +137,7 @@ namespace uniset
ChangeUndefinedStateSignal signal_change_undefined_state( uniset::ObjectId sid ); ChangeUndefinedStateSignal signal_change_undefined_state( uniset::ObjectId sid );
ChangeUndefinedStateSignal signal_change_undefined_state(); ChangeUndefinedStateSignal signal_change_undefined_state();
// ----------------------------------------------------------------------------------------- // -----------------------------------------------------------------------------------------
// полнейшее нарушение икапсуляции // полнейшее нарушение инкапсуляции
// но пока, это попытка оптимизировать работу с IOController через указатель. // но пока, это попытка оптимизировать работу с IOController через указатель.
// Т.е. работая с датчиками через итераторы.. // Т.е. работая с датчиками через итераторы..
#if 1 #if 1
...@@ -313,7 +313,7 @@ namespace uniset ...@@ -313,7 +313,7 @@ namespace uniset
void* getUserData( size_t index ); void* getUserData( size_t index );
void setUserData( size_t index, void* data ); void setUserData( size_t index, void* data );
// сигнал для реализации механизма зависимостией.. // сигнал для реализации механизма зависимостей..
// (все зависимые датчики подключаются к нему (см. NCRestorer::init_depends_signals) // (все зависимые датчики подключаются к нему (см. NCRestorer::init_depends_signals)
uniset::uniset_rwmutex changeMutex; uniset::uniset_rwmutex changeMutex;
ChangeSignal sigChange; ChangeSignal sigChange;
......
...@@ -56,9 +56,9 @@ namespace uniset ...@@ -56,9 +56,9 @@ namespace uniset
"заказчики" уведомляют \b IONC об изменении какого именно датчика они хотят получать уведомление, "заказчики" уведомляют \b IONC об изменении какого именно датчика они хотят получать уведомление,
после чего, если данный датчик меняет своё состояние, заказчику посылается после чего, если данный датчик меняет своё состояние, заказчику посылается
сообщение uniset::SensorMessage содержащее информацию о текущем(новом) состоянии датчика, сообщение uniset::SensorMessage содержащее информацию о текущем(новом) состоянии датчика,
времени изменения и т.п. В случае необходимости можно отказатся от уведомления. времени изменения и т.п. В случае необходимости можно отказаться от уведомления.
Для заказа датчиков предусмотрен ряд функций. На данный момент рекомендуется Для заказа датчиков предусмотрен ряд функций. На данный момент рекомендуется
пользоватся функцией IONotifyController::askSensor. пользоваться функцией IONotifyController::askSensor.
\b ConsumerMaxAttempts - максимальное число неудачных попыток послать сообщение "заказчику". \b ConsumerMaxAttempts - максимальное число неудачных попыток послать сообщение "заказчику".
Настраивается в конфигурационном файле. По умолчанию = 5. Настраивается в конфигурационном файле. По умолчанию = 5.
...@@ -112,7 +112,7 @@ namespace uniset ...@@ -112,7 +112,7 @@ namespace uniset
в AI11_AS будет записано значение -50. Как только Input4_S=1 в AI11_AS - появиться его истинное значение. в AI11_AS будет записано значение -50. Как только Input4_S=1 в AI11_AS - появиться его истинное значение.
\note Следует иметь ввиду, что для \b ЗАВИСИМОГО датчика функция setValue(..) действует как обычно и \note Следует иметь ввиду, что для \b ЗАВИСИМОГО датчика функция setValue(..) действует как обычно и
даже если он "заблокирован", значение в него можно сохранять. Оно "появиться" как только сниметься блокировка. даже если он "заблокирован", значение в него можно сохранять. Оно "появиться" как только снимется блокировка.
\section sec_NC_Optimization Оптимизация работы со списком "заказчиков" \section sec_NC_Optimization Оптимизация работы со списком "заказчиков"
Для оптимизации поиска списка заказчиков для конкретного датчика используется поле userdata (void*) у USensorInfo! Для оптимизации поиска списка заказчиков для конкретного датчика используется поле userdata (void*) у USensorInfo!
......
...@@ -134,7 +134,7 @@ namespace uniset ...@@ -134,7 +134,7 @@ namespace uniset
{ {
public: public:
const std::string sep = {"/"}; /*< раздедитель для имён подчинённых агрегаторов */ const std::string sep = {"/"}; /*< разделитель для имён подчинённых агрегаторов */
explicit LogAgregator( const std::string& name, Debug::type t ); explicit LogAgregator( const std::string& name, Debug::type t );
explicit LogAgregator( const std::string& name = "" ); explicit LogAgregator( const std::string& name = "" );
......
...@@ -82,7 +82,7 @@ namespace uniset ...@@ -82,7 +82,7 @@ namespace uniset
... ...
\endcode \endcode
\warning Логи отдаются "клиентам" только целоиком строкой. Т.е. по сети информация передаваться не будет пока не будет записан "endl". \warning Логи отдаются "клиентам" только целиком строкой. Т.е. по сети информация передаваться не будет пока не будет записан "endl".
Это сделано для "оптимизации передачи" (чтобы не передавать каждый байт) Это сделано для "оптимизации передачи" (чтобы не передавать каждый байт)
\warning Т.к. LogServer в основном только отдаёт "клиентам" логи, то он реализован с использованием CommonEventLoop, \warning Т.к. LogServer в основном только отдаёт "клиентам" логи, то он реализован с использованием CommonEventLoop,
......
...@@ -207,7 +207,7 @@ namespace uniset ...@@ -207,7 +207,7 @@ namespace uniset
// ------------------------------------------------------------------------ // ------------------------------------------------------------------------
/*! Собщение о срабатывании таймера */ /*! Сообщение о срабатывании таймера */
class TimerMessage : public Message class TimerMessage : public Message
{ {
public: public:
......
...@@ -101,7 +101,7 @@ namespace uniset ...@@ -101,7 +101,7 @@ namespace uniset
*/ */
bool list(const std::string& section, uniset::ListObjectName* ls, size_t how_many = 300) const; bool list(const std::string& section, uniset::ListObjectName* ls, size_t how_many = 300) const;
/*! Получние списка how_many подсекций из секции in_section. /*! Получение списка how_many подсекций из секции in_section.
* throw(uniset::ORepFailed); * throw(uniset::ORepFailed);
*/ */
bool listSections(const std::string& in_section, uniset::ListObjectName* ls, size_t how_many = 300) const; bool listSections(const std::string& in_section, uniset::ListObjectName* ls, size_t how_many = 300) const;
......
...@@ -111,7 +111,7 @@ namespace uniset ...@@ -111,7 +111,7 @@ namespace uniset
virtual void terminate() noexcept override; /*!< прервать работу таймера */ virtual void terminate() noexcept override; /*!< прервать работу таймера */
protected: protected:
timeout_t t_msec = { 0 }; /*!< интервал таймера, в милисекундах (для "пользователей") */ timeout_t t_msec = { 0 }; /*!< интервал таймера, в миллисекундах (для "пользователей") */
// Т.к. НЕ ВЕСЬ КОД переведён на использование std::chrono // Т.к. НЕ ВЕСЬ КОД переведён на использование std::chrono
// везде используется timeout_t (и WaitUpTime) // везде используется timeout_t (и WaitUpTime)
......
...@@ -37,7 +37,7 @@ namespace uniset ...@@ -37,7 +37,7 @@ namespace uniset
public: public:
// t1_msec - интервал "вкл" // t1_msec - интервал "вкл"
// t0_msec - интерфал "откл" // t0_msec - интервал "откл"
inline void run( timeout_t _t1_msec, timeout_t _t0_msec ) noexcept inline void run( timeout_t _t1_msec, timeout_t _t0_msec ) noexcept
{ {
setTiming(_t1_msec, _t0_msec, true); setTiming(_t1_msec, _t0_msec, true);
......
...@@ -79,7 +79,7 @@ namespace uniset ...@@ -79,7 +79,7 @@ namespace uniset
} }
// ----------------------------------------------------------------------------- // -----------------------------------------------------------------------------
// Просто обёртка для удобства вывода сообщений об ошибке в лог "объекта".. // Просто обёртка для удобства вывода сообщений об ошибке в лог "объекта"..
// "по задумке" позволяет не загромаждать код.. // "по задумке" позволяет не загромождать код..
// T - тип создаваемого объекта // T - тип создаваемого объекта
// M - (master) - класс который создаёт объект (подразумевается, что он UniSetManager) // M - (master) - класс который создаёт объект (подразумевается, что он UniSetManager)
// Использование // Использование
......
...@@ -91,7 +91,7 @@ namespace uniset ...@@ -91,7 +91,7 @@ namespace uniset
#ifndef DISABLE_REST_API #ifndef DISABLE_REST_API
// Поддрежка REST API (IHttpRequestRegistry) // Поддержка REST API (IHttpRequestRegistry)
virtual Poco::JSON::Object::Ptr httpGetByName( const std::string& name , const Poco::URI::QueryParameters& p ) override; virtual Poco::JSON::Object::Ptr httpGetByName( const std::string& name , const Poco::URI::QueryParameters& p ) override;
virtual Poco::JSON::Array::Ptr httpGetObjectsList( const Poco::URI::QueryParameters& p ) override; virtual Poco::JSON::Array::Ptr httpGetObjectsList( const Poco::URI::QueryParameters& p ) override;
virtual Poco::JSON::Object::Ptr httpHelpByName( const std::string& name, const Poco::URI::QueryParameters& p ) override; virtual Poco::JSON::Object::Ptr httpHelpByName( const std::string& name, const Poco::URI::QueryParameters& p ) override;
......
...@@ -68,7 +68,7 @@ namespace uniset ...@@ -68,7 +68,7 @@ namespace uniset
return uniset::ObjectType("UniSetManager"); return uniset::ObjectType("UniSetManager");
} }
// ------ функции объявленные в интерфейсе(IDL) ------ // ------ функции объявленые в интерфейсе(IDL) ------
virtual void broadcast( const uniset::TransportMessage& msg) override; virtual void broadcast( const uniset::TransportMessage& msg) override;
virtual uniset::SimpleInfoSeq* getObjectsInfo( CORBA::Long MaxLength = 300, const char* userparam = 0 ) override ; virtual uniset::SimpleInfoSeq* getObjectsInfo( CORBA::Long MaxLength = 300, const char* userparam = 0 ) override ;
......
...@@ -84,7 +84,7 @@ namespace uniset ...@@ -84,7 +84,7 @@ namespace uniset
UniSetObject(); UniSetObject();
virtual ~UniSetObject(); virtual ~UniSetObject();
// Функции объявленные в IDL // Функции объявленые в IDL
virtual CORBA::Boolean exist() override; virtual CORBA::Boolean exist() override;
virtual uniset::ObjectId getId() override; virtual uniset::ObjectId getId() override;
......
...@@ -34,7 +34,7 @@ namespace uniset ...@@ -34,7 +34,7 @@ namespace uniset
erBadCheckSum = 112, /*!< У пакета не сошлась контрольная сумма */ erBadCheckSum = 112, /*!< У пакета не сошлась контрольная сумма */
erBadReplyNodeAddress = 113, /*!< Ответ на запрос адресован не мне или от станции, которую не спрашивали */ erBadReplyNodeAddress = 113, /*!< Ответ на запрос адресован не мне или от станции, которую не спрашивали */
erTimeOut = 114, /*!< Тайм-аут при приеме ответа */ erTimeOut = 114, /*!< Тайм-аут при приеме ответа */
erPacketTooLong = 115, /*!< пакет длинее буфера приема */ erPacketTooLong = 115, /*!< пакет длиннее буфера приема */
erSessionClosed = 116 /*!< соединение закрыто */ erSessionClosed = 116 /*!< соединение закрыто */
}; };
......
...@@ -18,7 +18,7 @@ namespace uniset ...@@ -18,7 +18,7 @@ namespace uniset
Класс не самостоятельный и содержит "чисто" виртуальные функции Класс не самостоятельный и содержит "чисто" виртуальные функции
для реализации ответов на запросы. для реализации ответов на запросы.
\todo Разобратся с тем как отвечать на неправильные запросы! \todo Разобраться с тем как отвечать на неправильные запросы!
Формат ответных сообщений!!! Коды ошибок!!! Формат ответных сообщений!!! Коды ошибок!!!
\todo Доработать terminate, чтобы можно было прервать ожидание \todo Доработать terminate, чтобы можно было прервать ожидание
\todo Перейти на libev.. \todo Перейти на libev..
......
...@@ -20,11 +20,11 @@ namespace uniset ...@@ -20,11 +20,11 @@ namespace uniset
{ {
// ------------------------------------------------------------------------- // -------------------------------------------------------------------------
/*! ModbusTCPServer /*! ModbusTCPServer
* Реализация сервера на основе libev. Подерживается "много" соединений (постоянных). * Реализация сервера на основе libev. Поддерживается "много" соединений (постоянных).
* Хоть класс и наследуется от ModbusServer на самом деле он не реализует его функции, * Хоть класс и наследуется от ModbusServer на самом деле он не реализует его функции,
* каждое соединение обслуживается классом ModbusTCPSession. * каждое соединение обслуживается классом ModbusTCPSession.
* Но собственно реализаия функций одна на всех, это следует учитывать при реализации обработчиков, * Но собственно реализация функций одна на всех, это следует учитывать при реализации обработчиков,
* т.к.из многих "соединений" будут вызываться одни и теже обработатчики. * т.к.из многих "соединений" будут вызываться одни и те же обработчики.
*/ */
class ModbusTCPServer: class ModbusTCPServer:
public EventLoopServer, public EventLoopServer,
...@@ -34,7 +34,7 @@ namespace uniset ...@@ -34,7 +34,7 @@ namespace uniset
ModbusTCPServer( const std::string& addr, int port = 502 ); ModbusTCPServer( const std::string& addr, int port = 502 );
virtual ~ModbusTCPServer(); virtual ~ModbusTCPServer();
/*! Запуск сервера. Функция не возвращет управление. /*! Запуск сервера. Функция не возвращает управление.
* Но может быть прервана вызовом terminate() * Но может быть прервана вызовом terminate()
* \return FALSE - если не удалось запустить * \return FALSE - если не удалось запустить
*/ */
......
...@@ -28,7 +28,7 @@ namespace uniset ...@@ -28,7 +28,7 @@ namespace uniset
* а обработку делать по мере достаточного накопления данных во входной очереди, но это требует асинхронный * а обработку делать по мере достаточного накопления данных во входной очереди, но это требует асинхронный
* парсинг данных протокола modbus (т.е. мы анализируем очередной байт и решаем сколько нам нужно ещё * парсинг данных протокола modbus (т.е. мы анализируем очередной байт и решаем сколько нам нужно ещё
* "подождать" данных.. чтобы пойти на следующий шаг), это в результате будет слишком сложная реализация. * "подождать" данных.. чтобы пойти на следующий шаг), это в результате будет слишком сложная реализация.
* В конце-концов пока нет рассчёта на >1000 подключений (хотя libev позволяет держать >10k). * В конце-концов пока нет расчёта на >1000 подключений (хотя libev позволяет держать >10k).
*/ */
class ModbusTCPSession: class ModbusTCPSession:
public ModbusServerSlot, public ModbusServerSlot,
......
...@@ -1544,7 +1544,7 @@ namespace uniset ...@@ -1544,7 +1544,7 @@ namespace uniset
/*! проверка корректности данных */ /*! проверка корректности данных */
bool checkFormat() const; bool checkFormat() const;
// это поле служебное и не используется в релальном обмене // это поле служебное и не используется в реальном обмене
size_t count = { 0 }; /*!< фактическое количество данных */ size_t count = { 0 }; /*!< фактическое количество данных */
}; };
......
...@@ -3011,7 +3011,7 @@ namespace uniset ...@@ -3011,7 +3011,7 @@ namespace uniset
return "Неожидаемый тип пакета"; return "Неожидаемый тип пакета";
case erPacketTooLong: case erPacketTooLong:
return "пакет длинее буфера приема"; return "пакет длиннее буфера приема";
case erHardwareError: case erHardwareError:
return "ошибка оборудования"; return "ошибка оборудования";
......
...@@ -255,7 +255,7 @@ xmlNode* UniXML::copyNode(xmlNode* node, int recursive) ...@@ -255,7 +255,7 @@ xmlNode* UniXML::copyNode(xmlNode* node, int recursive)
спасает только такое вот дополнительное копирование списка свойств спасает только такое вот дополнительное копирование списка свойств
\bug Непонятный параметр 'target' \bug Непонятный параметр 'target'
- при указании NULL нормально работает - при указании NULL нормально работает
- при указании copynode - проблеммы с русским при сохранении - при указании copynode - проблемы с русским при сохранении
- при указании node - SEGFAULT при попытке удалить исходный(node) узел - при указании node - SEGFAULT при попытке удалить исходный(node) узел
\todo "Нужно тест написать на copyNode" \todo "Нужно тест написать на copyNode"
*/ */
......
...@@ -130,7 +130,7 @@ TEST_CASE("[DelayTimer]: debounce", "[DelayTimer]" ) ...@@ -130,7 +130,7 @@ TEST_CASE("[DelayTimer]: debounce", "[DelayTimer]" )
CHECK_FALSE( dt.check(false) ); CHECK_FALSE( dt.check(false) );
CHECK_FALSE( dt.get() ); CHECK_FALSE( dt.get() );
// проверяем срабатвание (одноразовый скачок) // проверяем срабатывание (одноразовый скачок)
CHECK_FALSE( dt.check(true) ); CHECK_FALSE( dt.check(true) );
CHECK_FALSE( dt.check(false) ); CHECK_FALSE( dt.check(false) );
msleep(160); msleep(160);
......
...@@ -44,7 +44,7 @@ class UModbus ...@@ -44,7 +44,7 @@ class UModbus
return uniset::ModbusRTU::isWriteFunction((uniset::ModbusRTU::SlaveFunctionCode)mbfunc); return uniset::ModbusRTU::isWriteFunction((uniset::ModbusRTU::SlaveFunctionCode)mbfunc);
} }
// выставление паметров связи, без установления соединения (!) // выставление параметров связи, без установления соединения (!)
void prepare( const std::string& ip, int port )throw(UException); void prepare( const std::string& ip, int port )throw(UException);
void connect( const std::string& ip, int port )throw(UException); void connect( const std::string& ip, int port )throw(UException);
......
...@@ -34,7 +34,7 @@ class UProxyObject_impl; // PIMPL ...@@ -34,7 +34,7 @@ class UProxyObject_impl; // PIMPL
* Перед активацией объекта необходимо при помощи addToAsk() добавить список датчиков, * Перед активацией объекта необходимо при помощи addToAsk() добавить список датчиков,
* за которыми требуется "следить". После активации ( см. PyUInterface uniset_activate_objects() ) * за которыми требуется "следить". После активации ( см. PyUInterface uniset_activate_objects() )
* (в асинхронном режиме!) объект заказывает датчики и сохраняет у себя их состояние. * (в асинхронном режиме!) объект заказывает датчики и сохраняет у себя их состояние.
* При этом "снаружи" можно запросить значение ранее добавленного датчика при помощи фунции getValue(). * При этом "снаружи" можно запросить значение ранее добавленного датчика при помощи функции getValue().
* Помимо этого можно изменять состояние датчиков (в SM!) при помощи setValue(). * Помимо этого можно изменять состояние датчиков (в SM!) при помощи setValue().
* По сути setValue() просто дублирует функциональность PyUInterface::setValue() * По сути setValue() просто дублирует функциональность PyUInterface::setValue()
*/ */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment