exponenta event banner

Обмен данными между сгенерированным и внешним кодом с помощью C API

Некоторые приложения Simulink ® Coder™ должны взаимодействовать с сигналами, состояниями, входами/выходами корневого уровня или параметрами в сгенерированном коде модели. Например, приложения калибровки контролируют и изменяют параметры. Приложения мониторинга сигнала или регистрации данных взаимодействуют с входными/выходными данными сигнала, состояния и корневого уровня. С помощью API Simulink Coder C можно создавать целевые приложения, регистрирующие сигналы, состояния и входы/выходы корневого уровня, сигналы мониторинга, состояния и входы/выходы корневого уровня, а также параметры настройки, в то время как генерируемый код выполняется.

C API минимизирует объем памяти, обмениваясь информацией, общей для сигналов, состояний, входов/выходов корневого уровня и параметров в небольших структурах. Структуры сигналов, состояний, входов/выходов корневого уровня и параметров включают индекс в карту структуры, позволяя нескольким сигналам, состояниям, входам/выходам корневого уровня или параметрам совместно использовать данные.

Для начала см. раздел Использование C API для доступа к модельным сигналам и состояниям или Использование C API для доступа к параметрам модели.

Сгенерированные файлы C API

При настройке модели для использования C API генератор кода Simulink Coder генерирует два дополнительных файла: model_capi.c (или .cpp) и model_capi.h, где model - имя модели. Генератор кода помещает два файла C API в папку сборки на основе настроек диалогового окна «Параметры конфигурации». Файл исходного кода C API содержит информацию о выходных сигналах глобального блока, состояниях, входах/выходах корневого уровня и глобальных параметрах, определенных в сгенерированном исходном коде модели кода. Файл заголовка C API представляет собой файл заголовка интерфейса между исходным кодом модели и сгенерированным C API. Для создания приложения можно использовать информацию в этих файлах C API. Среди созданных файлов - файлы, показанные на следующем рисунке.

Сгенерированные файлы с выбранным C API

Примечание

При настройке генератора кода для создания кода, включающего поддержку интерфейса C API и протоколирование данных, генератор кода может включать текст для имен блоков в пути блоков, зарегистрированных в файлах C API. model_capi.c (или .cpp) и model_capi.h. Если текст содержит символы, которые не представлены в кодировке набора символов для модели, генератор кода заменяет символы escape-последовательностями XML. Например, генератор кода заменяет японскую полноширинную букву Katakana ア на escape-последовательность ア. Дополнительные сведения см. в разделе Интернационализация и создание кода.

Создание файлов C API

Чтобы создать файлы C API для модели:

  1. Выберите интерфейс C API для модели. Существует два способа выбора интерфейса C API для модели, как описано в следующих разделах.

  2. Создайте код для модели.

После создания кода можно проверить файлы model_capi.c (или .cpp) и model_capi.h в папке построения модели.

Диалоговое окно «Выбор C API с параметрами конфигурации»

  1. Откройте модель и откройте диалоговое окно Параметры конфигурации (Configuration Parameters).

  2. На панели «Создание кода» > «Интерфейс» в подгруппе «Интерфейс обмена данными» выберите один или несколько C API варианты. В зависимости от выбранных параметров поддержка доступа к сигналам, параметрам, состояниям и корневому уровню ввода-вывода появится в сгенерированном коде C API.

    • Если требуется сгенерировать код C API для глобальных выходных блочных сигналов, выберите Генерировать C API для: сигналов.

    • Если требуется создать код C API для глобальных параметров блока, выберите «Создать C API для параметров:».

    • Если требуется создать код C API для дискретных и непрерывных состояний, выберите пункт Генерировать C API для: состояний.

    • Если вы хотите сгенерировать код C API для входов и выходов корневого уровня, выберите Generate C API for: root-level I/O.

Выберите C API из командной строки

В командной строке MATLAB ® можно использовать set_param для выбора или сброса параметров конфигурации модели C API. В командной строке MATLAB введите одну или несколько из следующих команд, где modelname - имя модели.

Чтобы выбрать Generate C API для сигналов, введите:

set_param('modelname','RTWCAPISignals','on')

Чтобы очистить API Generate C для сигналов, введите:

set_param('modelname','RTWCAPISignals','off')

Для выбора параметра Generate C API for: parameters введите:

set_param('modelname','RTWCAPIParams','on')

Чтобы снять флажок «Generate C API for: parameters», введите:

set_param('modelname','RTWCAPIParams','off')

Чтобы выбрать команду Генерировать C API для состояний, введите:

set_param('modelname','RTWCAPIStates','on')

Чтобы очистить API Generate C для состояний, введите:

set_param('modelname','RTWCAPIStates','off')

Для выбора пункта Generate C API for: root-level I/O введите:

set_param('modelname','RTWCAPIRootIO','on')

Чтобы очистить функцию Generate C API для ввода-вывода корневого уровня, введите:

set_param('modelname','RTWCAPIRootIO','off')

Описание файлов C API

Сведения о файлах C API

model_capi.c (или .cpp) предоставляет внешним приложениям согласованный интерфейс с данными модели. В зависимости от настроек конфигурации, данные могут представлять собой сигнал, состояние, вход или выход корневого уровня или параметр. В этом документе термин «элемент данных» относится либо к сигналу, либо к состоянию, входу или выходу корневого уровня, либо к параметру. API C использует структуры, которые обеспечивают интерфейс для свойств элемента данных. Интерфейс упаковывает свойства каждого элемента данных в структуру данных. Если модель содержит несколько элементов данных, интерфейс генерирует массив структур данных. Элементы структуры данных сопоставляются со свойствами данных.

Для взаимодействия с элементами данных приложению требуются следующие свойства для каждого элемента данных:

  • Имя

  • Путь к блоку

  • Номер порта (только для сигналов и входов/выходов корневого уровня)

  • Адрес

  • Сведения о типе данных: собственный тип данных, размер данных, сложность и другие атрибуты

  • Информация о размерах: количество строк, количество столбцов и ориентация данных (скалярная, векторная, матричная или n-мерная)

  • Информация с фиксированной точкой: наклон, смещение, тип масштаба, длина слова, экспонента и другие атрибуты

  • Информация о времени выборки (только для сигналов, состояний и входов/выходов корневого уровня): время выборки, идентификатор задачи, кадры

Как показано на следующем рисунке, свойства элемента А данных, например, находятся в структуре DS_A данных. Свойства элемента данных B находятся в структуре данных DS_B.

Некоторые значения свойств могут быть уникальными для каждого элемента данных, а некоторые значения свойств могут быть общими для нескольких элементов данных. Например, имя имеет уникальное значение для каждого элемента данных. Уникальные значения свойств помещаются непосредственно в структуру элемента данных. Значение имени элемента A данных находится в DS_A, а значение имени элемента B данных - в DS_B.

Но тип данных может быть свойством, значение которого имеет несколько элементов данных. Возможность некоторых элементов данных совместно использовать свойство позволяет C API иметь возможность повторного использования. В этом случае интерфейс помещает только значение индекса в DS_A и значение индекса в DS_B. Эти индексы указывают на другую структуру данных, DS_C, которая содержит фактическое значение типа данных. На следующем рисунке эта схема показана более подробно.

На рисунке показаны три сигнала. signal1 и signal2 совместно использовать один и тот же тип данных, double. Вместо указания этого значения типа данных в каждой структуре сигнальных данных интерфейс предоставляет только значение индекса 0 в структуре. "double" описывается записью 0 в rtDataTypeMap массив, на который ссылаются оба сигнала. Кроме того, значения свойств могут быть разделены между сигналами, состояниями, входами/выходами корневого уровня и параметрами, поэтому состояния, входы/выходы корневого уровня и параметры также могут ссылаться на double запись в rtDataTypeMap массив. Это повторное использование информации уменьшает размер памяти сгенерированного интерфейса.

Структурные массивы, созданные в файлах C API

Как и в случае типа данных, интерфейс отображает другие общие свойства (такие как адрес, измерение, масштабирование с фиксированной точкой и время выборки) в отдельные структуры и предоставляет индекс в структуре для элемента данных. Полный список определений структуры см. в файле matlabroot/rtw/c/src/rtw_capi.h. Этот файл также описывает каждый элемент в структуре. Массивы структуры, созданные в model_capi.c (или .cpp) файлы имеют типы структуры, определенные в rtw_capi.h файл. Ниже приведено краткое описание структурных массивов, созданных в model_capi.c (или .cpp):

  • rtBlockSignals - массив структур, содержащий информацию о выходных сигналах глобальных блоков в модели. Каждый элемент в массиве имеет тип struct rtwCAPI_Signals. Члены этой структуры предоставляют имя сигнала, путь к блоку, номер порта блока, адрес и индексы к типам данных, измерениям, массивам структур с фиксированной точкой и временем выборки.

  • rtBlockParameters - массив структур, содержащий информацию о перестраиваемых параметрах блока в модели по имени блока и имени параметра. Каждый элемент в массиве имеет тип struct rtwCAPI_BlockParameters. Члены этой структуры предоставляют имя параметра, путь блока, адрес и индексы для типов данных, измерений и массивов структуры с фиксированной точкой.

  • rtBlockStates - массив структур, содержащий информацию о дискретных и непрерывных состояниях в модели. Каждый элемент в массиве имеет тип struct rtwCAPI_States. Члены этой структуры предоставляют имя состояния, путь блока, тип (непрерывный или дискретный) и индексы к адресам, типу данных, измерению, массивам структур с фиксированной точкой и временем выборки.

  • rtRootInputs - массив структур, содержащий информацию о входных данных корневого уровня в модели. Каждый элемент в массиве имеет тип struct rtwCAPI_Signals. Члены этой структуры предоставляют входное имя корневого уровня, путь к блоку, номер порта блока, адрес и индексы к типам данных, измерениям, массивам структур с фиксированной точкой и временем выборки.

  • rtRootOutputs - массив структур, содержащий информацию о выходах корневого уровня в модели. Каждый элемент в массиве имеет тип struct rtwCAPI_Signals. Члены этой структуры предоставляют выходное имя корневого уровня, путь к блоку, номер порта блока, адрес и индексы к типам данных, измерениям, массивам структур с фиксированной точкой и временем выборки.

  • rtModelParameters - массив структур, содержащий информацию о переменных рабочего места, на которые ссылается один или несколько блоков или диаграмм Stateflow ® в модели в качестве параметров блоков. Каждый элемент массива имеет тип данныхrtwCAPI_ModelParameters. Члены этой структуры предоставляют имя переменной, адрес и индексы для типов данных, измерений и массивов структуры с фиксированной точкой.

  • rtDataAddrMap - массив базовых адресов сигналов, состояний, входов/выходов корневого уровня и параметров, которые появляются в rtBlockSignals, rtBlockParameters, rtBlockStates, и rtModelParameters массивы. Каждый элемент rtDataAddrMap массив является указателем на void (void*).

  • rtDataTypeMap - массив структур, содержащий информацию о различных типах данных в модели. Каждый элемент этого массива имеет тип struct rtwCAPI_DataTypeMap. Члены этой структуры предоставляют имя типа данных, размер типа данных и информацию о том, являются ли данные сложными.

  • rtDimensionMap - массив структур, содержащий информацию о различных измерениях данных в модели. Каждый элемент этого массива имеет тип struct rtwCAPI_DimensionMap. Члены этой структуры предоставляют информацию о количестве измерений в данных, ориентации данных (будь то скаляр, вектор или матрица) и фактических измерениях данных.

  • rtFixPtMap - массив структур, содержащий фиксированную информацию о сигналах, состояниях, входах/выходах корневого уровня и параметрах. Каждый элемент этого массива имеет тип struct rtwCAPI_FixPtMap. Члены этой структуры предоставляют информацию о масштабировании данных, смещении, степени и подписании данных с фиксированной точкой. Если модель не имеет данных с фиксированной точкой (сигнал, состояние, вход/выход корневого уровня или параметр), программа Simulink Coder назначает NULL или нулевые значения для элементов rtFixPtMap массив.

  • rtSampleTimeMap - массив структур, который содержит информацию выборки о глобальных сигналах, состояниях и входах/выходах корневого уровня в модели. (Этот массив не содержит сведений о параметрах.) Каждый элемент этого массива имеет тип struct rtwCAPI_SampleTimeMap. Члены этой структуры предоставляют информацию о периоде выборки, смещении и о том, основаны ли данные на кадрах или на выборках.

Создание файлов API примера C

Подтемы Сигналы C API, Состояния C API, Входы и выходы C API Root-Level и Параметры C API обсуждают сгенерированные структуры C API, используя пример модели rtwdemo_capi. Чтобы создать код из примерной модели, выполните следующие действия.

  1. Откройте модель, щелкнув значок rtwdemo_capi ссылка выше или путем ввода rtwdemo_capi в командной строке MATLAB.

  2. Если вы хотите создать структуры C API для входов/выходов корневого уровня в rtwdemo_capiвыберите параметр конфигурации модели Generate C API for: root-level I/O.

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

  3. Создайте код для модели.

Примеры кода C API в следующих подтемах создаются с C в качестве целевого языка.

Эта модель имеет три глобальных блочных выходных сигнала, которые будут отображаться в генерируемом C API коде:

  • top_sig1, которая является контрольной точкой на выходе блока Gain1 в верхней модели

  • sig2_eg, которая появляется в верхней модели и определяется в базовой рабочей области как Simulink.Signal объект, имеющий класс хранения ExportedGlobal

  • bot_sig1, которая появляется в ссылочной модели rtwdemo_capi_bot и определяется как Simulink.Signal объект, имеющий класс хранения Model default

Модель также имеет два дискретных состояния, которые появятся в сгенерированном коде C API:

  • top_state, которая определена для блока Delay1 в верхней модели

  • bot_state, который определен для блока дискретного фильтра в ссылочной модели

Модель имеет входы/выходы корневого уровня, которые появятся в сгенерированном коде C API, если выбрать параметр конфигурации модели Generate C API for: root-level I/O:

  • четыре входа корневого уровня, In1 через In4

  • Шесть выходов корневого уровня, Out1 через Out6

Кроме того, модель имеет пять глобальных параметров блоков, которые будут отображаться в генерируемом C API-коде:

  • Kp (верхняя модель Gain1 блок и ссылочная модель Gain2 блочный общий ресурс)

  • Ki (ссылочная модель Gain3 блок)

  • p1 (таблица подстановки lu1d)

  • p2 (таблица подстановки lu2d)

  • p3 (таблица подстановки lu3d)

Сигналы C API

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

Вот раздел кода в rtwdemo_capi_capi.c который предоставляет информацию о сигналах C API для верхней модели в rtwdemo_capi:

/* Block output signal information */
static const rtwCAPI_Signals rtBlockSignals[] = {
  /* addrMapIndex, sysNum, blockPath,
   * signalName, portNumber, dataTypeIndex, dimIndex, fxpIndex, sTimeIndex
   */
  { 0, 0, "rtwdemo_capi/Gain1",
    "top_sig1", 0, 0, 0, 0, 0 },

  { 1, 0, "rtwdemo_capi/lu2d",
    "sig2_eg", 0, 0, 1, 0, 0 },

  {
    0, 0, (NULL), (NULL), 0, 0, 0, 0, 0
  }
};

Примечание

Чтобы лучше понять код, прочитайте комментарии в файле. Например, обратите внимание на комментарий, который начинается в третьей строке предыдущего кода. В этом комментарии перечислены члены rtwCAPI_Signals структура, по порядку. Здесь указывается порядок, в котором для сигнала отображаются назначенные значения для каждого элемента. В этом примере комментарий говорит, что signalName является четвертым членом структуры. Первый сигнал описывается в следующих строках:

  { 0, 0, "rtwdemo_capi/Gain1",
    "top_sig1", 0, 0, 0, 0, 0 },

Из этих строк следует, что имя первого сигнала top_sig1.

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

  { 1, 0, "rtwdemo_capi/lu2d",
    "sig2_eg", 0, 0, 1, 0, 0 },

Этот сигнал, именованный sig2_eg, - выходной сигнал первого порта блока; rtwdemo_capi/lu2d. (Этот порт является первым портом, поскольку отсчитываемый от нуля индекс для portNumber отображаемому во второй строке присваивается значение 0.)

Адрес этого сигнала задается addrMapIndex, которая в данном примере отображается в первой строке как 1. Это обеспечивает индекс в rtDataAddrMap массив, найден позже в rtwdemo_capi_capi.c:

/* Declare Data Addresses statically */
static void* rtDataAddrMap[] = {
  &rtwdemo_capi_B.top_sig1,            /* 0: Signal */
  &sig2_eg[0],                         /* 1: Signal */
  &rtwdemo_capi_DWork.top_state,       /* 2: Discrete State */
  &rtP_Ki,                             /* 3: Model Parameter */
  &rtP_Kp,                             /* 4: Model Parameter */
  &rtP_p1[0],                          /* 5: Model Parameter */
  &rtP_p2[0],                          /* 6: Model Parameter */
  &rtP_p3[0],                          /* 7: Model Parameter */
};

Индекс 1 указывает на второй элемент в rtDataAddrMap массив. От rtDataAddrMap массив, можно сделать вывод, что адрес этого сигнала &sig2_eg[0].

Этот уровень косвенности поддерживает несколько экземпляров кода одной модели. В нескольких случаях информация о сигнале остается постоянной, за исключением адреса. В этом случае модель является единственным экземпляром. Следовательно, rtDataAddrMap объявляется статически. При создании многократно используемого кода создается функция инициализации, которая динамически инициализирует адреса для каждого экземпляра. Дополнительные сведения о создании многократно используемого кода см. в разделах Настройка генерации кода C для функций точек входа модели и Настройка поддержки повторного использования кода.

dataTypeIndex предоставляет индекс в rtDataTypeMap массив, найден позже в rtwdemo_capi_capi.c, указывающий тип данных сигнала:

/* Data Type Map - use dataTypeMapIndex to access this structure */
static const rtwCAPI_DataTypeMap rtDataTypeMap[] = {
  /* cName, mwName, numElements, elemMapIndex, dataSize, slDataId, *
   * isComplex, isPointer */
  { "double", "real_T", 0, 0, sizeof(real_T), SS_DOUBLE, 0, 0 }
};

Потому что индекс 0 для sig2_egиндекс указывает на первый структурный элемент в массиве. Можно сделать вывод, что тип данных сигнала - double. Значение isComplex является 0, указывая, что сигнал не является сложным. Вместо предоставления информации о типе данных непосредственно в rtwCAPI_Signals Вводят структуру, уровень косвенности. Параллелизм позволяет нескольким сигналам, которые совместно используют один и тот же тип данных, указывать на одну структуру карты, сохраняя память для каждого сигнала.

dimIndex (индекс размеров) обеспечивает индекс в rtDimensionMap массив, найден позже в rtwdemo_capi_capi.c, указывая размеры сигнала. Потому что этот индекс 1 для sig2_eg, индекс указывает на второй элемент в rtDimensionMap массив:

/* Dimension Map - use dimensionMapIndex to access elements of ths structure*/
static const rtwCAPI_DimensionMap rtDimensionMap[] = {
  /* dataOrientation, dimArrayIndex, numDims, vardimsIndex */
  { rtwCAPI_SCALAR, 0, 2, 0 },

  { rtwCAPI_VECTOR, 2, 2, 0 },
...
};

Из этой структуры можно сделать вывод, что это нескалярный сигнал, имеющий размерность 2. dimArrayIndex значение, 2, обеспечивает индекс в rtDimensionArray, найдено позже в rtwdemo_capi_capi.c:

/* Dimension Array- use dimArrayIndex to access elements of this array */
static const uint_T rtDimensionArray[] = {
  1,                                   /* 0 */
  1,                                   /* 1 */
  2,                                   /* 2 */
...
};

fxpIndex (индекс с фиксированной точкой) обеспечивает индекс в rtFixPtMap массив, найден позже в rtwdemo_capi_capi.c, указывая фиксированную информацию о сигнале. Ваш код может использовать информацию масштабирования для вычисления реального значения сигнала, используя уравнение V=SQ+Bгде V - «реальное» (то есть базовое-10) значение, S - заданный пользователем наклон, Q - «квантованное фиксированное значение» или «сохраненное целое число», а B - заданное пользователем смещение. Дополнительные сведения см. в разделе Масштабирование (конструктор фиксированных точек).

Потому что этот индекс 0 для sig2_eg, сигнал не имеет информации с фиксированной точкой. Нулевой индекс отображения с фиксированной точкой означает, что сигнал не имеет информации с фиксированной точкой.

sTimeIndex (индекс времени выборки) обеспечивает индекс для rtSampleTimeMap массив, найден позже в rtwdemo_capi_capi.c, указывая информацию о задаче о сигнале. При регистрации многоскоростных сигналов или условно выполненных сигналов может быть полезна информация выборки.

Примечание

model_capi.c (или .cpp) включает rtw_capi.h. Исходный файл, ссылающийся на rtBlockSignals массив также должен включать rtw_capi.h.

Состояния API C

rtwCAPI_States структура захватывает информацию о состоянии, включая имя состояния, адрес, путь блока, тип (непрерывный или дискретный), информацию о типе данных, информацию о размерах, информацию о фиксированных точках и информацию о времени выборки.

Вот раздел кода в rtwdemo_capi_capi.c которая предоставляет информацию о состояниях C API для верхней модели в rtwdemo_capi:

/* Block states information */
static const rtwCAPI_States rtBlockStates[] = {
  /* addrMapIndex, contStateStartIndex, blockPath,
   * stateName, pathAlias, dWorkIndex, dataTypeIndex, dimIndex,
   * fixPtIdx, sTimeIndex, isContinuous
   */
  { 2, -1, "rtwdemo_capi/Delay1",
    "top_state", "", 0, 0, 0, 0, 0, 0 },

  {
    0, -1, (NULL), (NULL), (NULL), 0, 0, 0, 0, 0, 0
  }
};

Каждый элемент массива, за исключением последнего, описывает состояние в модели. Конечный элемент массива является дозорным, при этом все элементы имеют нулевые значения. В этом примере код C API для модели верхнего уровня отображает одно состояние:

  { 2, -1, "rtwdemo_capi/Delay1",
    "top_state", "", 0, 0, 0, 0, 0, 0 },

Это состояние, с именем top_state, определяется для блока rtwdemo_capi/Delay1. Значение isContinuous равно нулю, что указывает на то, что состояние является дискретным, а не непрерывным. Другие поля соответствуют аналоговым эквивалентам сигналов, описанным в C API Signals, следующим образом:

  • Адрес сигнала задается addrMapIndex, которая, в данном примере, 2. Это индекс в rtDataAddrMap массив, найден позже в rtwdemo_capi_capi.c. Поскольку индекс основан на нуле, 2 соответствует третьему элементу в rtDataAddrMap, что является &rtwdemo_capi_DWork.top_state.

  • dataTypeIndex предоставляет индекс в rtDataTypeMap массив, найден позже в rtwdemo_capi_capi.c, указывая тип данных параметра. Значение 0 соответствует двойному некомплексному параметру.

  • dimIndex (индекс размеров) обеспечивает индекс в rtDimensionMap массив, найден позже в rtwdemo_capi_capi.c. Значение 0 соответствует первой записи, которая { rtwCAPI_SCALAR, 0, 2, 0 }.

  • fixPtIndex (индекс с фиксированной точкой) обеспечивает индекс в rtFixPtMap массив, найден позже в rtwdemo_capi_capi.c, указывая фиксированную информацию о параметре. Как и в случае соответствующего атрибута сигнала, нулевой индекс отображения с фиксированной точкой означает, что параметр не имеет информации с фиксированной точкой.

Входы и выходы на корневом уровне C API

rtwCAPI_Signals структура захватывает входную/выходную информацию корневого уровня, включая имя ввода/вывода, адрес, путь блока, номер порта, информацию о типе данных, информацию о размерах, информацию о фиксированных точках и информацию о времени выборки. (Эта структура также используется для блочных выходных сигналов, как описано ранее в C API Signals.)

Вот раздел кода в rtwdemo_capi_capi.c которая предоставляет информацию о входах/выходах корневого уровня C API для верхней модели в rtwdemo_capi:

/* Root Inputs information */
static const rtwCAPI_Signals rtRootInputs[] = {
  /* addrMapIndex, sysNum, blockPath,
   * signalName, portNumber, dataTypeIndex, dimIndex, fxpIndex, sTimeIndex
   */
  { 3, 0, "rtwdemo_capi/In1",
    "", 1, 0, 0, 0, 0 },

  { 4, 0, "rtwdemo_capi/In2",
    "", 2, 0, 0, 0, 0 },

  { 5, 0, "rtwdemo_capi/In3",
    "", 3, 0, 0, 0, 0 },

  { 6, 0, "rtwdemo_capi/In4",
    "", 4, 0, 0, 0, 0 },

  {
    0, 0, (NULL), (NULL), 0, 0, 0, 0, 0
  }
};

/* Root Outputs information */
static const rtwCAPI_Signals rtRootOutputs[] = {
  /* addrMapIndex, sysNum, blockPath,
   * signalName, portNumber, dataTypeIndex, dimIndex, fxpIndex, sTimeIndex
   */
  { 7, 0, "rtwdemo_capi/Out1",
    "", 1, 0, 0, 0, 0 },

  { 8, 0, "rtwdemo_capi/Out2",
    "", 2, 0, 0, 0, 0 },

  { 9, 0, "rtwdemo_capi/Out3",
    "", 3, 0, 0, 0, 0 },

  { 10, 0, "rtwdemo_capi/Out4",
    "", 4, 0, 0, 0, 0 },

  { 11, 0, "rtwdemo_capi/Out5",
    "sig2_eg", 5, 0, 1, 0, 0 },

  { 12, 0, "rtwdemo_capi/Out6",
    "", 6, 0, 1, 0, 0 },

  {
    0, 0, (NULL), (NULL), 0, 0, 0, 0, 0
  }
};

Для получения информации о интерпретации значений в rtwCAPI_Signals см. предыдущий раздел «Сигналы API C».

Параметры C API

rtwCAPI_BlockParameters и rtwCAPI_ModelParameters структуры захватывают информацию о параметрах, включая имя параметра, путь блока (для параметров блока), адрес, информацию о типе данных, информацию о размерах и информацию о фиксированных точках.

rtModelParameters массив содержит записи для переменных рабочей области, на которые ссылаются как на настраиваемые параметры блока Simulink или данные потока состояния области компьютера. Например, настраиваемые параметры включают Simulink.Parameter объекты, использующие класс хранения, отличный от Auto. Программное обеспечение Simulink Coder назначает только свои элементы NULL или нулевые значения при отсутствии таких данных.

Настройка, выбранная для параметра конфигурации модели Поведение параметра по умолчанию (Default parameter behavior), определяет, как информация генерируется в rtBlockParameters массив в model_capi.c (или .cpp).

  • Если для параметра Поведение по умолчанию (Default parameter behavior Tunable, rtBlockParameters содержит запись для каждого изменяемого параметра каждого блока в модели. Однако если для задания параметра блока используется переменная MATLAB или настраиваемый параметр, параметр блока не отображается в rtBlockParameters. Вместо этого переменная или настраиваемый параметр появляется в rtModelParameters.

  • Если для параметра Поведение по умолчанию (Default parameter behavior) задано значение Inlined, rtBlockParameters пуст массив. Программное обеспечение Simulink Coder назначает только свои элементы NULL или нулевые значения.

Последний элемент каждого массива является дозорным, все элементы которого имеют нулевые значения.

Вот rtBlockParameters массив, сгенерированный по умолчанию в rtwdemo_capi_capi.c:

/* Individual block tuning is not valid when inline parameters is *
 * selected. An empty map is produced to provide a consistent     *
 * interface independent  of inlining parameters.                 *
 */
static const rtwCAPI_BlockParameters rtBlockParameters[] = {
  /* addrMapIndex, blockPath,
   * paramName, dataTypeIndex, dimIndex, fixPtIdx
   */
  {
    0, (NULL), (NULL), 0, 0, 0
  }
};

В этом примере генерируется только последний контрольный элемент массива со всеми членами структуры. rtwCAPI_BlockParameters установить в значение NULL и нулевые значения. Это связано с тем, что для поведения параметра по умолчанию установлено значение Inlined по умолчанию для rtwdemo_capi пример модели. Если для параметра Поведение по умолчанию (Default parameter behavior) задано значение Tunableпараметры блока генерируются в rtwCAPI_BlockParameters структура. Однако переменные MATLAB и настраиваемые параметры отображаются в rtwCAPI_ModelParameters структура.

Вот rtModelParameters массив, сгенерированный по умолчанию в rtwdemo_capi_capi.c:

/* Tunable variable parameters */
static const rtwCAPI_ModelParameters rtModelParameters[] = {
  /* addrMapIndex, varName, dataTypeIndex, dimIndex, fixPtIndex */
  { 2, TARGET_STRING("Ki"), 0, 0, 0 },

  { 3, TARGET_STRING("Kp"), 0, 0, 0 },

  { 4, TARGET_STRING("p1"), 0, 2, 0 },

  { 5, TARGET_STRING("p2"), 0, 3, 0 },

  { 6, TARGET_STRING("p3"), 0, 4, 0 },

  { 0, (NULL), 0, 0, 0 }
};

В этом примере rtModelParameters содержит записи для каждой переменной, на которую ссылаются как на настраиваемый параметр блока Simulink.

Например, varName (имя переменной) четвертого параметра p2. Другие поля соответствуют аналоговым эквивалентам сигналов, описанным в C API Signals, следующим образом:

  • Адрес четвертого параметра задается addrMapIndex, которая, в данном примере, 5. Это индекс в rtDataAddrMap массив, найден позже в rtwdemo_capi_capi.c. Поскольку индекс основан на нуле, 5 соответствует шестому элементу в rtDataAddrMap, что является rtP_p2.

  • dataTypeIndex предоставляет индекс в rtDataTypeMap массив, найден позже в rtwdemo_capi_capi.c, указывая тип данных параметра. Значение 0 соответствует двойному некомплексному параметру.

  • dimIndex (индекс размеров) обеспечивает индекс в rtDimensionMap массив, найден позже в rtwdemo_capi_capi.c. Значение 3 соответствует четвертой записи, которая { rtwCAPI_MATRIX_COL_MAJOR, 6, 2, 0 }.

  • fixPtIndex (индекс с фиксированной точкой) обеспечивает индекс в rtFixPtMap массив, найден позже в rtwdemo_capi_capi.c, указывая фиксированную информацию о параметре. Как и в случае соответствующего атрибута сигнала, нулевой индекс отображения с фиксированной точкой означает, что параметр не имеет информации с фиксированной точкой.

Дополнительные сведения о настраиваемом хранении параметров в сгенерированном коде см. в разделе Как сгенерированный код хранит внутренний сигнал, состояние и данные параметров.

Сопоставить структуры данных API C с rtModel

Структура данных модели в реальном времени инкапсулирует данные модели и связанную с ними информацию, которая полностью описывает модель. При выборе функции C API и генерации кода генератор кода Simulink Coder добавляет другой элемент в структуру данных модели в реальном времени, созданную в model.h:

/*
 * DataMapInfo:
 * The following substructure contains information regarding
 * structures generated in the model's C API.
 */
struct {
  rtwCAPI_ModelMappingInfo mmi;
} DataMapInfo;

Этот член определяет mmi (для информации о отображении модели) типа struct rtwCAPI_ModelMappingInfo. Сооружение расположено в matlabroot/rtw/c/src/rtw_modelmap.h. mmi подструктура определяет интерфейс между моделью и файлами C API. Более конкретно, члены mmi сопоставить структуру данных модели в реальном времени со структурами в model_capi.c (или .cpp).

Инициализация значений mmi элементы в массивах выполняют сопоставление, как показано в сопоставлении модели с массивами структур API C. Каждый член указывает на один из массивов структур в созданном файле C API. Например, адрес rtBlockSignals массив структур выделен первому члену mmi подструктура в model.c (или .cpp), используя следующий код в rtw_modelmap.h файл:

/* signals */
struct {
    rtwCAPI_Signals const *signals;     /* Signals Array */
    uint_T                numSignals;   /* Num Signals   */
    rtwCAPI_Signals const *rootInputs;  /* Root Inputs array */
    uint_T               numRootInputs; /* Num Root Inputs  */
    rtwCAPI_Signals const *rootOutputs; /* Root Outputs array */
    uint_T               numRootOutputs;/* Num Root Outputs  */
} Signals;

Функция инициализации модели в model.c (или .cpp) выполняет инициализацию путем вызова функции инициализации C API. Например, следующий код генерируется в функции инициализации модели, например, модели rtwdemo_capi:

/* Initialize DataMapInfo substructure containing ModelMap for C API */
rtwdemo_capi_InitializeDataMapInfo(rtwdemo_capi_M);

Сопоставить модель с массивами структур API C

Примечание

На этом рисунке перечислены массивы в том порядке, в котором они расположены rtw_modelmap.h, который немного отличается от их сгенерированного порядка в model_capi.c.

Создание файла определения данных C API для обмена данными с целевой системой

В этом примере показано, как использовать целевой C-API для взаимодействия с сгенерированным кодом, который представляет сигналы, состояния, параметры и операции ввода/вывода корневого уровня.

Открыть пример модели

Открыть пример модели rtwdemo_capi.

open_system('rtwdemo_capi');

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

1. Настройте протокол клиент/сервер (например, TCP/IP или двухпортовое соединение памяти) между компьютером разработки и целевым компьютером.

2. Выберите хотя бы один из параметров конфигурации модели C API: сигналы, параметры, состояния и корневой уровень ввода/вывода.

3. Настройте элементы данных, к которым требуется получить доступ с помощью C API с адресными классами хранения.

Настройки конфигурации C API для модели верхнего уровня и ссылочных моделей должны совпадать.

Генератор кода помещает интерфейс C API в файл model_capi.c. В зависимости от настроек конфигурации, данные могут представлять сигналы, состояния, параметры и операции ввода-вывода корневого уровня, сконфигурированные с адресными классами хранения. Файл включает структуры, которые обеспечивают интерфейс для свойств данных.

Ограничения API C

Функция C API имеет следующие ограничения.

  • API C не поддерживает следующие значения для CodeFormat Переменная TLC:

    • S-Function

    • Accelerator_S-Function (для ускоренного моделирования)

  • Для целевых объектов на основе ERT API C требует включить поддержку кода с плавающей запятой.

  • Выходные сигналы локальных блоков не поддерживаются.

  • Параметры локального потока состояний не поддерживаются.

  • Следующие пользовательские объекты класса хранения не поддерживаются:

    • Объекты без пакета csc_registration файл

    • Сгруппированные пользовательские классы хранения

    • Объекты, определенные с помощью макросов

    • BitField объекты

    • FileScope объекты

  • Настраиваемое размещение данных отключается при использовании C API. Интерфейс ищет объявление глобальных данных в model.h и model_private.h. Объявления, помещенные в любой другой файл с помощью настраиваемого размещения данных, приводят к тому, что код не компилируется.

Примечание

Объекты Custom Storage Class работают при создании кода, только если используется целевой файл системы ERT и очищается параметр конфигурации модели Ignore custom storage classes.

Связанные темы