Формат общих областей памяти ПО прибора

При старте диспетчера расчётных модулей он выделяет в системе под свои нужды несколько областей памяти.

Область памяти /header описывается следующей структурой:

typedefstruct
{
 char name_disp[STR_LEN]; /* Имя диспетчера*/
 int takt; /* Базовай такт работы, мсек */
 int number_exemod; /* Количество расчетных модулей*/
 int num; /* Количество внешних сигналов */
 int signals_size; /* Количество байт занимаемое сигналами*/
 int pid; /* Пид. диспетчера*/
 int takt_counter; /* Локальный счётчик тактов диспетчера */
} header;

Здесь представлены следующие элементы:

name_disp имя файла конфигурации загрузки, указанное при старте диспетчера;
takt базовый (минимальный из всех заданных в файле конфигурации загрузки) такт работы в мсек, используется для расчёта текущего времени при отладке;
number_exemod количество загруженных расчетных модулей (алгоритмов);
num общее количество внешних сигналов (равно сумме всех к-в внешних сигналов для всех РМ), используется для поиска по области памяти /extvars_struct;
signals_size количество памяти в байтах, выделенное под все внешние сигналы при запуске диспетчера;
pid идентификатор процесса, необходимый для трансляции диспетчеру сообщений и управления через сервер отладки;
takt_counter счётчик количества циклов посылок сообщений функции takt_work диспетчера расчётных модулей.

Данная область памяти используется расчётными модулями и сервером отладки для подключения к нужным переменным в общей области памяти, а также для управления диспетчером РМ.

Область памяти /exemod_struct содержит информацию о текущих загруженных расчётных модулях и состоит из записей типа: количество структур = количеству расчётных модулей в /header, представлено ниже:

typedefstruct
{
 Char exename[STR_LEN];
 Char algname[STR_LEN];
 int offset;
 int takt_mod;
 int tek_time;
 int num_work;
 int pid; 
 int chid;
 int coid;
 int din_vars_bytes;
 int alg_vars_bytes;
 int state_vars_bytes;
 int constants_bytes;
 int number_extvars;
 unsigned char flag_error; 
 char error_name[256];
} exemod_data;

В этой структуре представлены следующие элементы:

exename имя расчетного модуля (исполняемого файла);
algname имя алгоритма, указываемое в файле конфигурации загрузки;
offset начальное смещение расчетного модуля в общем массиве структур сигналов (область памяти /extvars_struct);
takt_mod такт работы расчетного модуля в мс, заданный в файле конфигурации загрузки (см. предыдущий пункт);
tek_time текущее время до начала исполнения, мс. Когда текущее время становится равным нулю, модуль запускается на счет. Описание как эта переменная используется можно посмотреть в функции takt_work, исходный текст которой приведён в предыдущем разделе справки;
num_work количество вызовов за один такт;
pid идентификатор процесса расчетного модуля;
chid идентификатор канала обмена в ОСРВ версии QNX6 (в версии QNX4 – параметр не используется);
coid идентификатор клиента, используемый в MsgSend для посылки сообщений от диспетчера расчётному модулю (только для ОСРВ версии QNX 6, в версии QNX4 параметр не используется);
din_vars_bytes размер области памяти динамических переменных, выделенных в общей памяти расчётным модулем, байт. Необходим для работы отладочного сервера;
alg_vars_bytes размер области памяти алгебраических переменных, выделенных в общей памяти расчётным модулем, байт. Необходим для работы отладочного сервера;
state_vars_bytes размер области памяти переменных состояния, выделенных в общей памяти расчётным модулем, байт. Необходим для работы отладочного сервера;
constants_bytes размер области памяти констант, выделенных в общей памяти расчётным модулем, байт. Необходим для работы отладочного сервера;
number_extvars количество внешних сигналов;
flag_error признак ошибки диспетчера РМ, если эта переменная больше нуля, значит в системе возникла ошибка (например произошло отключение расчётного модуля или время вычисления расчётного модуля не укладывается в заданный такт);
error_name описание ошибки – строка, размером не более 256 символов в формате ASCII.

Область памяти /extvars_struct содержит описание всех внешних переменных, выделенных при загрузке диспетчером и состоит из записей типа ext_var_info_record. В поле index для каждой из структур при этом содержится байтовое смещение переменной для единой области памяти хранящей значения внешних переменных ( /extvars_value ).

Алгоритм поиска внешней переменной в расчётном модуле следующий:

1) из /header получаем количество загруженных расчетных модулей;

2) по имени алгоритма для заданного запущенного расчётного модуля производим поиск по имени в области памяти /exemod_struct нужной структуры exemod_data, которая описывает алгоритм. Именно поэтому имя алгоритма при запуске расчетного модуля должно обязательно указываться;

3) из структуры exemod_data получаем начальный индекс в массиве структур внешних переменных для расчетного модуля, находим начало описания внешних переменных расчетного модуля в области памяти /extvars_struct;

4) последовательно считываем данные о смещениях ext_var_info_record.index внешних переменных, хранящихся в общей области разделяемой памяти нужных расчетных модулей (количество внешних переменных расчетного модуля определено).

Пример как производить поиск внешней переменной для осуществления перепаковки данных или иной обработке данных, можно посмотреть в следующем разделе справки, а также в исходных кодах расчётного модуля (calc\calcmain.c). Пример поиска внешней переменной в области памяти по имени приведен в Приложении А.

Схематично алгоритм поиска адреса внешней переменной при загрузке расчётного модуля представлен на рисунке:

Общая область памяти /extvars_value, выделяется диспетчером при запуске расчётных модулей и содержит в себе текущие значения для всех внешних переменных, используемых по всех РМ. При загрузке каждый из РМ получает адреса нужных ему внешних переменных в данной области памяти по вышеприведённому алгоритму.

Кроме указанных выше областей памяти, выделяемых диспетчером расчётных модулей перед загрузкой всех РМ, каждый из них при старте выделяет общие области памяти под свои внутренние переменные. Внутренние переменные, в отличие от внешних, не объединяются. Выделяемые области памяти – это рабочие массивы, в которых последовательно расположены значения внутренних переменных, приём для разного класса внутренних переменных выделяются разные области памяти:

/din_vars_<имя алгоритма указанное при запуске>

/alg_vars_<имя алгоритма указанное при запуске>

/state_vars_vars_<имя алгоритма указанное при запуске>

/constants_vars_<имя алгоритма указанное при запуске>