Из-за ограничений, описанных в, Генерируют Повторно используемый Код от Подсистем, генератор кода не может снова использовать сгенерированный код, как вы ожидаете. Чтобы определить, почему код, сгенерированный для подсистемы, не снова используется:
Рассмотрите раздел Subsystems отчета генерации кода.
Сравните данные о контрольной сумме подсистемы.
Если генератор кода не генерирует код для подсистемы как повторно используемый код, и вы сконфигурировали подсистему как допускающую повторное использование, исследуйте раздел Subsystems отчета генерации кода (см., Генерируют Отчет Генерации кода). Раздел Subsystems содержит:
Таблица, которая подводит итог, как невиртуальные подсистемы были преобразованы в сгенерированный код.
Диагностическая информация, которая описывает, почему подсистемы не были сгенерированы как повторно используемый код.
Раздел Subsystems также сопоставляет невстроенные подсистемы в модели к функциям или снова использованным функциям в сгенерированном коде. Для примера откройте и создайте модель rtwdemo_atomic
.
Можно определить, почему код подсистемы не снова используется путем сравнения данных о контрольной сумме подсистемы. Генератор кода определяет, идентичны ли подсистемы путем сравнения контрольных сумм подсистемы, как отмечено в Ограничениях. Для повторного использования подсистемы через модели, на которые ссылаются эта процедура не может отметить каждое различие.
Рассмотрите модель, rtwdemo_ssreuse
. SS1
и SS2
являются экземплярами той же подсистемы. В обоих экземплярах параметр подсистемы Function packaging установлен в Reusable function
.
Используйте метод Simulink.SubSystem.getChecksum
, чтобы получить контрольную сумму для подсистемы. Рассмотрите результаты определить, почему код не снова используется.
Откройте модель rtwdemo_ssreuse
. Сохраните копию в папке модели, где у вас есть доступ для записи.
Сопоставьте подсистемы SS1
и SS2
с gcb
. Для каждой из подсистем, в окне модели, выбирают подсистему. В то время как подсистема выбрана в Командном окне, введите:
SS1 = gcb;
SS2 = gcb;
Используйте метод Simulink.SubSystem.getChecksum
, чтобы получить контрольную сумму для каждой подсистемы. Этот метод возвращает два выходных значения: значение контрольной суммы и детали о входе раньше вычисляли контрольную сумму.
[chksum1, chksum1_details] = ... Simulink.SubSystem.getChecksum(SS1); [chksum2, chksum2_details] = ... Simulink.SubSystem.getChecksum(SS2);
Сравните два значения контрольной суммы. Значения должны быть равными на основе настроек подсистемы.
isequal(chksum1, chksum2) ans = 1
Чтобы использовать Simulink.SubSystem.getChecksum
, чтобы определить, почему контрольные суммы двух подсистем отличаются, измените режим типа данных выходного порта SS1 так, чтобы это отличалось от того из SS2.
Посмотрите под маской SS1
. Щелкните правой кнопкой по подсистеме. В контекстном меню выберите Mask Look Under Mask.
В блок-схеме подсистемы дважды кликните блок Lookup Table, чтобы открыть диалоговое окно Subsystem Parameters.
Нажмите Data Types.
Выберите Saturate on integer overflow и нажмите OK.
Получите контрольную сумму для SS1
. Сравните контрольные суммы для этих двух подсистем. На этот раз контрольные суммы не равны.
[chksum1, chksum1_details] = ... Simulink.SubSystem.getChecksum(SS1); isequal(chksum1, chksum2) ans = 0
После того, как вы решите, что контрольные суммы отличаются, узнают почему. Механизм Simulink® использует информацию, такую как типы данных сигнала, некоторые значения параметров блоков, и информация о возможности соединения блока, чтобы вычислить контрольные суммы. Чтобы определить, почему контрольные суммы отличаются, сравните данные, которые вычисляют значения контрольной суммы. Можно получить эту информацию от второго значения, возвращенного Simulink.SubSystem.getChecksum
, который является массивом структур с четырьмя полями.
Посмотрите на структуру chksum1_details
.
chksum1_details chksum1_details = ContentsChecksum: [1x1 struct] InterfaceChecksum: [1x1 struct] ContentsChecksumItems: [287x1 struct] InterfaceChecksumItems: [53x1 struct]
ContentsChecksum
и InterfaceChecksum
являются контрольными суммами компонента контрольной суммы подсистемы. Остающиеся два поля, ContentsChecksumItems
и InterfaceChecksumItems
, содержат детали контрольной суммы.
Определите, существует ли различие в содержимом подсистемы, интерфейсе или обоих. Например:
isequal(chksum1_details.ContentsChecksum.Value,... chksum2_details.ContentsChecksum.Value) ans = 0 isequal(chksum1_details.InterfaceChecksum.Value,... chksum2_details.InterfaceChecksum.Value) ans = 1
В этом случае различия существуют в содержимом.
Запишите скрипт как этот скрипт, чтобы найти различия.
idxForCDiffs=[]; for idx = 1:length(chksum1_details.ContentsChecksumItems) if (~strcmp(chksum1_details.ContentsChecksumItems(idx).Identifier, ... chksum2_details.ContentsChecksumItems(idx).Identifier)) disp(['Identifiers different for contents item ', num2str(idx)]); idxForCDiffs=[idxForCDiffs, idx]; end if (ischar(chksum1_details.ContentsChecksumItems(idx).Value)) if (~strcmp(chksum1_details.ContentsChecksumItems(idx).Value, ... chksum2_details.ContentsChecksumItems(idx).Value)) disp(['Character vector values different for contents item ', num2str(idx)]); idxForCDiffs=[idxForCDiffs, idx]; end end if (isnumeric(chksum1_details.ContentsChecksumItems(idx).Value)) if (chksum1_details.ContentsChecksumItems(idx).Value ~= ... chksum2_details.ContentsChecksumItems(idx).Value) disp(['Numeric values different for contents item ', num2str(idx)]); idxForCDiffs=[idxForCDiffs, idx]; end end end
Запустите скрипт. Пример принимает, что вы назвали скрипт check_details
.
check_details Character vector values different for contents item 202
Результаты показывают, что различия существуют для индексного пункта 202 в содержимом подсистемы.
Используйте возвращенные индексные значения, чтобы получить указатель, идентификатор и детали значения для каждого найденного различия.
chksum1_details.ContentsChecksumItems(202) ans = Handle: 'rtwdemo_ssreuse/SS1/Lookup Table' Identifier: 'SaturateOnIntegerOverflow' Value: 'on'
Детали идентифицируют параметры блоков Интерполяционной таблицы Saturate on integer overflow как особое внимание для отладки проблемы повторного использования подсистемы.