1. 程式人生 > >[Simulink] System Target File學習筆記

[Simulink] System Target File學習筆記

Code Generation

在這裡插入圖片描述

System target file

Target Language Compiler 是程式碼生成工具, Simulink Coder/Embedded Coder 會使用這個工具,去執行 .tlc 檔案。 tlc 檔案裡描述瞭如何將 .rtw 變成程式碼。

程式碼生成用到的 .tlc 檔案是一系列,而不是單單是一個或者一類。

%% SYSTLC: STM32F4 Target TMF: ert_default_tmf MAKE: make_rtw EXTMODE: ext_comm
%selectfile NULL_FILE
%assign CodeFormat = "Embedded-C"
%assign TargetType = "RT"
%assign Language   = "C"
%include "codegenentry.tlc"

/%
  BEGIN_RTW_OPTIONS
  %----------------------------------------%
  % Configure RTW code generation settings %
  %----------------------------------------%
  rtwgensettings.BuildDirSuffix = '_stm32f4';
  rtwgensettings.DerivedFrom = 'ert.tlc';
  rtwgensettings.Version = '1';
  END_RTW_OPTIONS
%/

第1行的註釋%% SYSTLC: STM32F4 Target TMF: ert_default_tmf MAKE: make_rtw EXTMODE: ext_comm對屬性進行了描述,告訴Simulink環境,該系統目標檔案支援哪些功能,這裡支援

  • 支援生成mk檔案的tmf模板
  • 支援mk的命令
  • 支援外部命令
    %selectfile NULL_FILE,要做一個函式級的或非指令碼型別的,寫這句。
    %assign CodeFormat = "Embedded-C",定義變數,說明支援生成程式碼的型別為嵌入式C程式碼
    %assign TargetType = "RT"
    ,生成程式碼的目標型別為實時硬體
    %assign Language = "C",生成C語言程式碼

另外還有其他的命令,如下:
%assign AutoBuildProcedure = !GenerateSampleERTMain不生成模板的ert檔案

這條命令的作用等同於下圖中黃色部分
在這裡插入圖片描述


%include "commontargetlib.tlc",將commontargetlib.tlc展開執行
%include "codegenentry.tlc",將codegenentry.tlc展開執行

tlc檔案的後半部分為巨集定義,以/% BEGIN_RTW_OPTIONS

開頭,以/% END_RTW_OPTIONS結束,定義了使用者選擇該tlc檔案後,Code Generation的設定以及該欄下方的Tab欄顯示內容。

巨集定義

上面的例項中沒有對Tab欄顯示內容做修改,下面的例子(ST公司提供的STM32-MAT-TARGET支援包)給出了新增Tab欄顯示內容的例項:

%% SYSTLC: stm32 (Embedded Target) TMF: stm32.tmf MAKE: make_rtw \
%%    EXTMODE: ext_comm

%selectfile NULL_FILE

%%
%% System Target File for stm32
%%
%% $ stm32.tlc 2009-05-14 dlange $
%%

%assign CodeFormat = "Embedded-C"
%assign TargetType = "RT"
%assign Language   = "C"

%include "codegenentry.tlc"

/%
  BEGIN_RTW_OPTIONS

  oIdx = 1;

  rtwoptions(oIdx).prompt        = 'STM32 Options';
  rtwoptions(oIdx).type          = 'Category';
  rtwoptions(oIdx).enable        = 'on';  
  rtwoptions(oIdx).default       = 8;
  rtwoptions(oIdx).popupstrings  = '';
  rtwoptions(oIdx).tlcvariable   = '';
  rtwoptions(oIdx).tooltip       = '';
  rtwoptions(oIdx).callback      = '';
  rtwoptions(oIdx).makevariable  = '';

  
   oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'Download Application';
  rtwoptions(oIdx).type           = 'Checkbox';
  rtwoptions(oIdx).default        = 'on';
  rtwoptions(oIdx).tlcvariable    = 'DownloadApplication';
  rtwoptions(oIdx).makevariable   = 'DOWNLOADAPPLICATION';
  rtwoptions(oIdx).tooltip        = ...
    ['Select to open STM32 generated project.'];
  rtwoptions(oIdx).callback      = '';

  oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'STM32CubeMx Path update';
  rtwoptions(oIdx).type           = 'Checkbox';
  rtwoptions(oIdx).default        = 'off';
  rtwoptions(oIdx).tlcvariable    = 'STM32CubeMxPathUpdate';
  rtwoptions(oIdx).makevariable   = 'STM32CUBEMXPATHUPDATE';
  rtwoptions(oIdx).tooltip        = ...
    ['Get STM32CubeMx path from registry. Uncheck to modify path manually.'];
  rtwoptions(oIdx).callback       = 'stm32cubemxpath_callback(hDlg, hSrc, ''STM32CubeMxPathUpdate'')';
   
  oIdx = oIdx + 1;
   
  rtwoptions(oIdx).prompt         = 'STM32CubeMx installation path';
  rtwoptions(oIdx).type           = 'Edit';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).tlcvariable    = 'STM32CubeMxPath';
  rtwoptions(oIdx).makevariable   = 'STM32CUBEMXPATH';
  rtwoptions(oIdx).enable         = 'on';
  rtwoptions(oIdx).tooltip        = ...
    ['installation path for STM32CubeMx'];
  rtwoptions(oIdx).callback      = 'stm32cubemxpath_callback(hDlg, hSrc, ''STM32CubeMxPath'')';
 
  oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'Installed Path';
  rtwoptions(oIdx).type           = 'NonUI';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).tlcvariable    = 'Target_Inst_path';
  rtwoptions(oIdx).makevariable   = 'TARGET_INST_PATH';
  rtwoptions(oIdx).enable         = 'off';
  rtwoptions(oIdx).tooltip        = '';
  rtwoptions(oIdx).callback      = ''; 
  
  oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'Installed Full Path';
  rtwoptions(oIdx).type           = 'Edit';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).tlcvariable    = 'Target_Inst_Fullpath';
  rtwoptions(oIdx).makevariable   = 'TARGET_INST_FULLPATH';
  rtwoptions(oIdx).enable         = 'off';
  rtwoptions(oIdx).tooltip        = ...
    ['Path to package added with pathtool command.'];
  rtwoptions(oIdx).callback      = ''; 
 
  oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'Update installed path';
  rtwoptions(oIdx).type           = 'Pushbutton';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).tlcvariable    = 'UpdateInstalledPath';
  rtwoptions(oIdx).makevariable   = 'UPDATEINSTALLEDPATH';
  rtwoptions(oIdx).tooltip        = ...
    ['Click to automatically update package installation path.'];
  rtwoptions(oIdx).callback       = 'stm32updatepath_callback(hDlg, hSrc)';
 
   oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'Model configuration (ioc) Full Path';
  rtwoptions(oIdx).type           = 'Edit';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).tlcvariable    = 'Ioc_Fullpath';
  rtwoptions(oIdx).makevariable   = 'IOC_FULLPATH';
  rtwoptions(oIdx).enable         = '';
  rtwoptions(oIdx).tooltip        = ...
    ['Path to ioc configuration file.'];
  rtwoptions(oIdx).callback      = ''; 
 
   oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'Interrupt Handler Optimization';
  rtwoptions(oIdx).type           = 'Checkbox';
  rtwoptions(oIdx).default        = 'on';
  rtwoptions(oIdx).tlcvariable    = 'IT_Handler_Optim';
  rtwoptions(oIdx).makevariable   = 'IT_HANDLER_OPTIM';
  rtwoptions(oIdx).tooltip        = ...
    ['HAL IRQ Handler not generated from STM32CubeMX. Code is not generated in HAL callback function but directly in IRQ Handler. '];
  rtwoptions(oIdx).callback      = '';

  oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt        = 'STM32 Project Files';
  rtwoptions(oIdx).type          = 'Category';
  rtwoptions(oIdx).enable        = 'on';  
  rtwoptions(oIdx).default       = 5;
  rtwoptions(oIdx).popupstrings  = '';
  rtwoptions(oIdx).tlcvariable   = '';
  rtwoptions(oIdx).tooltip       = '';
  rtwoptions(oIdx).callback      = '';
  rtwoptions(oIdx).makevariable  = '';
  
  oIdx = oIdx + 1;
  
  rtwoptions(oIdx).prompt         = 'Append to list';
  rtwoptions(oIdx).type           = 'Checkbox';
  rtwoptions(oIdx).enable         = '';
  rtwoptions(oIdx).default        = 'on';
  rtwoptions(oIdx).popupstrings   = '';
  rtwoptions(oIdx).tlcvariable    = 'STM32AppendToList';
  rtwoptions(oIdx).makevariable   = '';
  rtwoptions(oIdx).tooltip        = ...
    ['Files and paths selected will be appended to the list'];
  rtwoptions(oIdx).callback       = '';
  
  oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'Select source files (.c)';
  rtwoptions(oIdx).type           = 'Pushbutton';
  rtwoptions(oIdx).enable         = '';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).popupstrings   = '';
  rtwoptions(oIdx).tlcvariable    = 'UpdateCFilelist';
  rtwoptions(oIdx).makevariable   = '';
  rtwoptions(oIdx).tooltip        = ...
    ['Click to open multiselect window'];
  rtwoptions(oIdx).callback       = 'stm32updateCfileList_callback(hDlg, hSrc, ''STM32AppendToList'')';
 
  oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'C files included to project';
  rtwoptions(oIdx).type           = 'Edit';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).tlcvariable    = 'CProjectFiles';
  rtwoptions(oIdx).makevariable   = '';
  rtwoptions(oIdx).enable         = '';
  rtwoptions(oIdx).tooltip        = ...
    ['C files include functions that can be called from Simulink MATLAB Function'];
  rtwoptions(oIdx).callback      = '';
  rtwoptions(oIdx).popupstrings   = '';

  oIdx = oIdx + 1;

  rtwoptions(oIdx).prompt         = 'Select include files (.h)';
  rtwoptions(oIdx).type           = 'Pushbutton';
  rtwoptions(oIdx).enable         = '';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).popupstrings   = '';
  rtwoptions(oIdx).tlcvariable    = 'UpdateHPathlist';
  rtwoptions(oIdx).makevariable   = '';
  rtwoptions(oIdx).tooltip        = ...
    ['Click to open multiselect window'];
  rtwoptions(oIdx).callback       = 'stm32updateHPathList_callback(hDlg, hSrc, ''STM32AppendToList'')';
  
  oIdx = oIdx + 1;
 
  rtwoptions(oIdx).prompt         = 'Header files added to project';
  rtwoptions(oIdx).type           = 'Edit';
  rtwoptions(oIdx).default        = '';
  rtwoptions(oIdx).tlcvariable    = 'HPathFiles';
  rtwoptions(oIdx).makevariable   = '';
  rtwoptions(oIdx).enable         = '';
  rtwoptions(oIdx).tooltip        = ...
    ['Header files included for C functions that can be called from Simulink MATLAB Function'];
  rtwoptions(oIdx).callback      = '';
  rtwoptions(oIdx).popupstrings   = '';
 

  %----------------------------------------%
  % Configure RTW code generation settings %
  %----------------------------------------%

  rtwgensettings.DerivedFrom = 'ert.tlc';
  rtwgensettings.BuildDirSuffix = '_stm32';
  rtwgensettings.Version = '1';
  rtwgensettings.SelectCallback = ['stm32_SelectCallback(hDlg, hSrc)'];
  %rtwgensettings.ActivateCallback = ['stm32_ActivateCallback(hDlg, hSrc)'];
  rtwgensettings.PostApplyCallback = ['stm32_PostApplyCallback(hDlg, hSrc)'];
 

  END_RTW_OPTIONS
 %/

%% [EOF]: stm32.tlc

程式碼生成配置

/%
  BEGIN_RTW_OPTIONS
  %----------------------------------------%
  % Configure RTW code generation settings %
  %----------------------------------------%
  rtwgensettings.BuildDirSuffix = '_stm32f4';
  rtwgensettings.DerivedFrom = 'ert.tlc';
  rtwgensettings.Version = '1';
  END_RTW_OPTIONS
%/

rtwgensettings.BuildDirSuffix = '_stm32f4'; 設定程式碼生成的資料夾名字
rtwgensettings.DerivedFrom = 'ert.tlc'; 繼承ert.tlc的模板


另外,在 % Configure RTW code generation settings % 中還有回撥函式的定義,這裡給出autosar.tlc的例項,具體程式碼段如下:

/%

  BEGIN_RTW_OPTIONS

  rtwoptions = autosar_rtwoptions_callback('GetOptions', rtwoptions);

  rtwgensettings.BuildDirSuffix = '_autosar_rtw';
  rtwgensettings.Version        = autosarcore.rtwOptions('GetRtwOptionsVersion');
  rtwgensettings.SelectCallback = 'autosar_rtwoptions_callback(''SelectCallBack'', hSrc, hDlg)';
  rtwgensettings.ActivateCallback = 'autosar_rtwoptions_callback(''ActivateCallBack'', hSrc, hDlg)';
  rtwgensettings.DerivedFrom = 'ert.tlc';
  
  END_RTW_OPTIONS
 %/

這裡出現了兩個回撥函式

  rtwgensettings.SelectCallback = 'autosar_rtwoptions_callback(''SelectCallBack'', hSrc, hDlg)';
  rtwgensettings.ActivateCallback = 'autosar_rtwoptions_callback(''ActivateCallBack'', hSrc, hDlg)';

回撥函式格式為:

% 在Code Generation的TLC選擇框內選擇該tlc檔案後執行哪些動作 
% 這個callback_handler可以由使用者自行定義
rtwgensettings.SelectCallback =callback_handler(hDlg,hSrc);
rtwgensettings.ActivateCallback = callback_handler(hDlg,hSrc);
rtwgensettings.PostApplyCallback = callback_handler(hDlg,hSrc);

callback_handler例項

callback_handler可以以.m的函式檔案放置到tlc檔案所在路徑下。下面給出一個具體的例項(該例項為SCANeR提供的ert_scanerapi_select.m)

function ert_scanerapi_select(hDlg, hSrc)
slConfigUISetVal(hDlg, hSrc, 'StopTime', 'inf');
slConfigUISetVal(hDlg, hSrc, 'SolverType', 'Fixed-step');
slConfigUISetVal(hDlg, hSrc, 'Solver', 'FixedStepDiscrete');
slConfigUISetVal(hDlg, hSrc, 'SupportContinuousTime', 'on');
slConfigUISetVal(hDlg, hSrc, 'SupportNonInlinedSFcns', 'on');
slConfigUISetVal(hDlg, hSrc, 'GenerateSampleERTMain', 'off');
slConfigUISetEnabled(hDlg, hSrc, 'GenerateSampleERTMain', false);
slConfigUISetVal(hDlg, hSrc, 'ModelReferenceCompliant', 'on');
% slConfigUISetEnabled(hDlg, hSrc, 'ModelReferenceCompliant', false);

其中,hDlg為configuration parameters的控制代碼,hSrc為模型的控制代碼,slConfigUISetVal為Simulink的built-in函式,一共4個引數,前兩個為hDlghSrc,後面兩個為要設定的引數名對應的引數值slConfigUISetEnabled同理,設定enabled用。

【提示】要檢視引數名,在Configuration Parameters的對話方塊內需要檢視的內容處右鍵,what’s This?後檢視,如圖。
在這裡插入圖片描述
點選show more information後可以檢視該引數的具體設定:
在這裡插入圖片描述
如果是針對嵌入式開發,callback_handler中可以將下列命令引入:

function ert_example_select(hDlg, hSrc)
% 設定固定點步長,並禁止修改
slConfigUISetVal(hDlg, hSrc, 'SolverType', 'Fixed-step');
slConfigUISetEnabled(hDlg, hSrc, 'SolverType', 'off');
% 設定離散求解器
slConfigUISetVal(hDlg, hSrc, 'Solver', 'FixedStepDiscrete');
% 設定預設取樣時間
slConfigUISetVal(hDlg, hSrc, 'FixedStep', '0.1');
% 設定內聯引數
% 高版本的MATLAB中這個引數修改為Default parameter behavior ?
slConfigUISetVal(hDlg, hSrc, 'InlineParams', 'on');
% 生成報告
slConfigUISetVal(hDlg, hSrc, 'GenerateReport', 'on');
% 自動開啟報告
slConfigUISetVal(hDlg, hSrc, 'LaunchReport', 'on');
% 只生成程式碼
slConfigUISetVal(hDlg, hSrc, 'GenCodeOnly', 'on');
% 不生成makefile(不生成可執行檔案,不需要makefile檔案)
slConfigUISetVal(hDlg, hSrc, 'GenerateMakefile', 'off');
% 生成註釋
slConfigUISetVal(hDlg, hSrc, 'GenerateComments', 'on');
% 生成A2L檔案
slConfigUISetVal(hDlg, hSrc, 'GenerateASAP2', 'on');

使用for迴圈改寫上面的.m回撥函式:

function ert_example_select_for_loop(hDlg, hSrc)

configs = {'SolverType','on';
                  'Solver','FixedStepDiscrete';
                  'FixedStep', '0.1';
                  'InlineParams', 'on';
                  'GenerateReport', 'on';
                  'LaunchReport', 'on';
                  'GenCodeOnly', 'on';
                  'GenerateMakefile', 'off';
                  'GenerateComments', 'on';
                  'GenerateASAP2', 'on';};

for i = 1:length(configs)
    slfConfigUISetVal(hDlg,hSrc,configs{i,1},configs{i,2});
end
 
slConfigUISetEnabled(hDlg, hSrc, 'SolverType', 'off');

在實際建模時,可以將修改system target file的命令放置到某個config模組的回撥函式中,這樣,只要拖入該模組,就可以實現自動將系統目標檔案修改的目的。
【注意】 下面兩個命令可以在Matlab的command windows中對Simulink模型的system target file進行修改。
disableimplicitsignalresolution(bdroot);
set_param(bdroot,‘SystemTargetFile’,‘ert_example.tlc’)
連結:https://pan.baidu.com/s/1-q1a8Kt4D9SU-AaG-qODIw
提取碼:5aax