www.gusucode.com > ecoder 案例源码程序 matlab代码 > ecoder/ConfigureDataInterfaceFeaturedExample.m
%% Configure Data Interface by Applying Custom Storage Classes % To integrate the generated code with your own handwritten code, you can % configure data items in a model, such as signal lines and block % parameters, % to appear in the generated code as global variables. Use custom storage classes and custom data types to: % % * Export or import named numeric data types (|typedef|). % * Control placement of declarations and definitions in exported and % imported files. % * Package multiple data items into structures. % * Apply the storage type qualifiers |const| and |volatile|. %% Explore Example Model % Open the example model <matlab:rtwdemo_advsc |rtwdemo_advsc|>. rtwdemo_advsc %% % The model creates |Simulink.Parameter| and |Simulink.Signal| data objects in % the base workspace. The names of the signal objects match the names of % signal lines and block states in the model diagram. Blocks in the model use the parameter % objects to set parameter values. You can use the objects to configure % code generation settings for these data items. % % Update the diagram to display the signal data types. Many of the % signals use the custom data type |MYTYPE|. In the base workspace, a % |Simulink.NumericType| object, |MYTYPE|, acts as an alias for the % double-precision, floating-point % data type |double|. In the property dialog box, the property *Is alias* % is selected. %% Configure Data Representation Through Custom Storage Classes % Suppose that you want to configure the generated code to: % % * Import the definitions (memory allocation) and declarations of the input signals |input1| % through |input4| from your handwritten code. You provide the % declarations in a header file named |inputSigs.h| and the definitions in a % source file named |globalSigs.c|. % * Export the declaration of the output signal |output| to a generated header file % named |outSig.h|. % * Export all of the parameters, such as |K1|, as fields of a global structure variable. % * Apply the qualifier |volatile| to the Unit Delay block state |X| and to the data store |mode|. % % To achieve these goals, apply custom storage classes to the data items. % % Open the Model Explorer. daexplr %% % In the *Model Hierarchy* pane, select the node *Base Workspace*. The data % objects appear in the *Contents* pane. % % In the *Contents* pane, set *Column View* to |Storage Class|. % % Select the |Simulink.Signal| objects |input1| through |input4|. Use the % *StorageClass* column to apply the custom storage class |ImportFromFile| % to all four objects. Use the *HeaderFile* column to specify the header % file name, |inputSigs.h|. % % <<../batch_edit.png>> % % Alternatively, to configure the objects, at the command prompt, use these commands: input1.CoderInfo.StorageClass = 'Custom'; input1.CoderInfo.CustomStorageClass = 'ImportFromFile'; input1.CoderInfo.CustomAttributes.HeaderFile = 'inputSigs.h'; input2.CoderInfo.StorageClass = 'Custom'; input2.CoderInfo.CustomStorageClass = 'ImportFromFile'; input2.CoderInfo.CustomAttributes.HeaderFile = 'inputSigs.h'; input3.CoderInfo.StorageClass = 'Custom'; input3.CoderInfo.CustomStorageClass = 'ImportFromFile'; input3.CoderInfo.CustomAttributes.HeaderFile = 'inputSigs.h'; input4.CoderInfo.StorageClass = 'Custom'; input4.CoderInfo.CustomStorageClass = 'ImportFromFile'; input4.CoderInfo.CustomAttributes.HeaderFile = 'inputSigs.h'; %% % To include the handwritten source file |globalSigs.c| when Simulink Coder compiles and links the % generated code, you can use a configuration parameter such as % *Configuration Parameters > Code Generation > Custom Code > Additional % Build Information > Source files*. % % Apply the custom storage class |ExportToFile| to the signal object % |output|. Specify the header file |outSig.h|. output.CoderInfo.StorageClass = 'Custom'; output.CoderInfo.CustomStorageClass = 'ExportToFile'; output.CoderInfo.CustomAttributes.HeaderFile = 'outSig.h'; %% % Use the Model Explorer to apply the custom storage class |Struct| to all of the parameter objects. % Set *StructName* to |paramStruct|. K1.CoderInfo.StorageClass = 'Custom'; K1.CoderInfo.CustomStorageClass = 'Struct'; K1.CoderInfo.CustomAttributes.StructName = 'paramStruct'; K2.CoderInfo.StorageClass = 'Custom'; K2.CoderInfo.CustomStorageClass = 'Struct'; K2.CoderInfo.CustomAttributes.StructName = 'paramStruct'; LOWER.CoderInfo.StorageClass = 'Custom'; LOWER.CoderInfo.CustomStorageClass = 'Struct'; LOWER.CoderInfo.CustomAttributes.StructName = 'paramStruct'; UPPER.CoderInfo.StorageClass = 'Custom'; UPPER.CoderInfo.CustomStorageClass = 'Struct'; UPPER.CoderInfo.CustomAttributes.StructName = 'paramStruct'; T1Break.CoderInfo.StorageClass = 'Custom'; T1Break.CoderInfo.CustomStorageClass = 'Struct'; T1Break.CoderInfo.CustomAttributes.StructName = 'paramStruct'; T1Data.CoderInfo.StorageClass = 'Custom'; T1Data.CoderInfo.CustomStorageClass = 'Struct'; T1Data.CoderInfo.CustomAttributes.StructName = 'paramStruct'; T2Break.CoderInfo.StorageClass = 'Custom'; T2Break.CoderInfo.CustomStorageClass = 'Struct'; T2Break.CoderInfo.CustomAttributes.StructName = 'paramStruct'; T2Data.CoderInfo.StorageClass = 'Custom'; T2Data.CoderInfo.CustomStorageClass = 'Struct'; T2Data.CoderInfo.CustomAttributes.StructName = 'paramStruct'; %% % Apply the custom storage class |Volatile| to the signal objects |X| and % |mode|. X.CoderInfo.StorageClass = 'Custom'; X.CoderInfo.CustomStorageClass = 'Volatile'; mode.CoderInfo.StorageClass = 'Custom'; mode.CoderInfo.CustomStorageClass = 'Volatile'; %% % To export the data type definition (|typedef|) of |MYTYPE| from the generated code, % configure the |DataScope| property of the data type object |MYTYPE| by using either the command % prompt or the property dialog box. % Export the definition to a header file named |myTypes.h|. MYTYPE.DataScope = 'Exported'; MYTYPE.HeaderFile = 'myTypes.h'; %% % You can include this exported header file in the handwritten % source file |globalSigs.c| in which you allocate memory for the input signals |input1| % through |input4|. %% Generate and Inspect Code % Generate code from the model. Before you generate code, select % *Configuration Parameters > Generate code only*. set_param('rtwdemo_advsc','GenCodeOnly','on') rtwbuild('rtwdemo_advsc') %% % In the code generation report, view the shared file |myTypes.h|. The file % uses |typedef| statements to define the real and complex data types % |MYTYPE| and |cMYTYPE|. file = fullfile('slprj','ert','_sharedutils','myTypes.h'); rtwdemodbtype(file,'typedef real_T MYTYPE;','typedef creal_T cMYTYPE;',1,1) %% % View the shared file |outsig.h|. The file uses the |extern| keyword to export % the declaration of the output signal |output|. file = fullfile('slprj','ert','_sharedutils','outSig.h'); rtwdemodbtype(file,'/* Exported data declaration */','extern MYTYPE output;',1,1) %% % View the file |rtwdemo_advsc_private.h|. The file uses a |#include| statement to % include the imported header file |inputSigs.h|. % % View the file |rtwdemo_advsc.h|. The file defines a structure type that % contains a field for each of the parameter objects. file = fullfile('rtwdemo_advsc_ert_rtw','rtwdemo_advsc.h'); rtwdemodbtype(file,'/* Type definition for custom storage class: Struct */','} paramStruct_type;',1,1) %% % View the file |rtwdemo_advsc.c|. The file allocates memory for the % exported signal |output|, the parameter structure, the state |X|, and the % data store |mode|. The definitions of the state and the data store use % the qualifier |volatile|. file = fullfile('rtwdemo_advsc_ert_rtw','rtwdemo_advsc.c'); rtwdemodbtype(file,'/* Exported data definition */','volatile boolean_T mode;',1,1) %% Store Model Data in Data Dictionary % When you end your MATLAB session, variables that you create in the base workspace do not persist. % To permanently store data objects and data type objects, consider linking the % model to a data dictionary. % % # In the example model, select *File > Model Properties % > Link to Data Dictionary*. % # In the Model Properties dialog box, select *Data Dictionary*. Click % *New*. % # In the Create a new Data Dictionary dialog box, set *File name* to % |myDict| and click *Save*. In the Model Properties dialog box, click *OK*. % # Click *Yes* in response to the message about migrating base workspace data. Click *Yes* in % response to the message about removing the imported items from the base % workspace. % % Alternatively, to manually migrate the data into % a data dictionary, you can use programmatic commands: % Create a list of the variables and objects that the target % model uses. usedVars = {Simulink.findVars('rtwdemo_advsc').Name}; % Create a new data dictionary in your current folder. Link the model to % this new dictionary. myDictObj = Simulink.data.dictionary.create('myDict.sldd'); set_param('rtwdemo_advsc','DataDictionary','myDict.sldd') % Import only the target variables from the base workspace to the data % dictionary. importFromBaseWorkspace(myDictObj,'clearWorkspaceVars',true,'varList',usedVars); %% % The data dictionary now permanently stores the objects that the model % uses. To view the contents of the dictionary, click the data dictionary % badge in the lower-left corner of the model. % % You can configure data characteristics, including % code generation settings such as custom storage classes, without creating % and storing data objects in a workspace or data dictionary. For more information, see % <docid:ecoder_ug.br0debj>.