Function Reuse in Generated Code
This example shows how to configure an atomic subsystem for generating reusable code. To specify that the code generated for a subsystem execute as an atomic unit, on the Block Parameters dialog box, select the Treat as atomic unit parameter. That parameter enables the Function Packaging parameter on the Code Generation tab. The Function Packaging parameter has these four settings:
Inline
: Inline the subsystem codeNonreusable function
: Function with I/O passed as global dataReusable function
: Function with I/O passed as function argumentsAuto
: Let Simulink Coder optimize based on context
The Reusable function
and Auto
settings permit the code generator to reuse subsystem code. The Reusable function
and Nonreusable function
settings enable the Function name options, Function name, and File name options parameters.
If you have an Embedded Coder® license, you can configure a nonreusable subsystem to accept arguments.
Example Model
The GeneratedCodeFunctionReuse
model contains two identical subsystems, SS1
and SS2
. For these subsystems, the Function packaging parameter is set to Reusable
function
, and the Function name parameter is myfun
. The subsystems are parameterized masked subsystems. To see the contents of the masked subsystems, right-click the subsystem blocks and select Mask > Look Under Mask.
model = 'GeneratedCodeFunctionReuse';
open_system(model);
Generate and Inspect Code
Open the Simulink Coder or Embedded Coder app. Then, generate and inspect the code.
slbuild(model)
### Starting build procedure for: GeneratedCodeFunctionReuse ### Successful completion of build procedure for: GeneratedCodeFunctionReuse Build Summary Top model targets: Model Build Reason Status Build Duration ============================================================================================================================= GeneratedCodeFunctionReuse Information cache folder or artifacts were missing. Code generated and compiled. 0h 0m 11.171s 1 of 1 models built (0 models already up to date) Build duration: 0h 0m 11.968s
cfile=fullfile(pwd, 'GeneratedCodeFunctionReuse_grt_rtw', 'GeneratedCodeFunctionReuse.c'); coder.example.extractLines(cfile, '/* Model step', '/* Model initialize', 1, 0);
/* Model step function */ void GeneratedCodeFunctionReuse_step(void) { /* Outputs for Atomic SubSystem: '<Root>/SS1' */ /* Inport: '<Root>/In1' incorporates: * Inport: '<Root>/In2' */ myfun(GeneratedCodeFunctionReuse_U.In1, GeneratedCodeFunctionReuse_U.In2, GeneratedCodeFunctionReuse_P.T1Data, GeneratedCodeFunctionReuse_P.T1Break, &GeneratedCodeFunctionReuse_B.SS1); /* End of Outputs for SubSystem: '<Root>/SS1' */ /* Outport: '<Root>/Out1' */ GeneratedCodeFunctionReuse_Y.Out1 = GeneratedCodeFunctionReuse_B.SS1.LookupTable; /* Outputs for Atomic SubSystem: '<Root>/SS2' */ /* Inport: '<Root>/In1' incorporates: * Inport: '<Root>/In2' */ myfun(GeneratedCodeFunctionReuse_U.In1, GeneratedCodeFunctionReuse_U.In2, GeneratedCodeFunctionReuse_P.T2Data, GeneratedCodeFunctionReuse_P.T2Break, &GeneratedCodeFunctionReuse_B.SS2); /* End of Outputs for SubSystem: '<Root>/SS2' */ /* Outport: '<Root>/Out2' */ GeneratedCodeFunctionReuse_Y.Out2 = GeneratedCodeFunctionReuse_B.SS2.LookupTable; }
In the model step function, there are two calls to the reusable function, myfun
. The mask parameters, T1Break
, T1Data
, T2Break
, and T2Data
, are function arguments.
Change the Function Packaging parameter to Inline
.
set_param('GeneratedCodeFunctionReuse/SS1','RTWSystemCode','Inline') set_param('GeneratedCodeFunctionReuse/SS2','RTWSystemCode','Inline')
Generate and inspect the code.
slbuild(model)
### Starting build procedure for: GeneratedCodeFunctionReuse ### Successful completion of build procedure for: GeneratedCodeFunctionReuse Build Summary Top model targets: Model Build Reason Status Build Duration ========================================================================================================= GeneratedCodeFunctionReuse Generated code was out of date. Code generated and compiled. 0h 0m 7.5587s 1 of 1 models built (0 models already up to date) Build duration: 0h 0m 8.3447s
cfile=fullfile(pwd, 'GeneratedCodeFunctionReuse_grt_rtw', 'GeneratedCodeFunctionReuse.c'); coder.example.extractLines(cfile, '/* Model step', '/* Model initialize', 1, 0);
/* Model step function */ void GeneratedCodeFunctionReuse_step(void) { real_T Out1_tmp; /* Outputs for Atomic SubSystem: '<Root>/SS2' */ /* Outputs for Atomic SubSystem: '<Root>/SS1' */ /* Sum: '<S1>/Sum' incorporates: * Inport: '<Root>/In1' * Inport: '<Root>/In2' * Sum: '<S2>/Sum' */ Out1_tmp = GeneratedCodeFunctionReuse_U.In1 + GeneratedCodeFunctionReuse_U.In2; /* End of Outputs for SubSystem: '<Root>/SS2' */ /* Outport: '<Root>/Out1' incorporates: * Lookup_n-D: '<S1>/Lookup Table' * Sum: '<S1>/Sum' */ GeneratedCodeFunctionReuse_Y.Out1 = look1_binlx(Out1_tmp, GeneratedCodeFunctionReuse_P.T1Break, GeneratedCodeFunctionReuse_P.T1Data, 10U); /* End of Outputs for SubSystem: '<Root>/SS1' */ /* Outputs for Atomic SubSystem: '<Root>/SS2' */ /* Outport: '<Root>/Out2' incorporates: * Lookup_n-D: '<S2>/Lookup Table' */ GeneratedCodeFunctionReuse_Y.Out2 = look1_binlx(Out1_tmp, GeneratedCodeFunctionReuse_P.T2Break, GeneratedCodeFunctionReuse_P.T2Data, 10U); /* End of Outputs for SubSystem: '<Root>/SS2' */ }
In the model step function, the subsystem code is inlined.
Change the Function Packaging parameter to Nonreusable function
. For SS2
, change the Function name parameter to myfun2
.
set_param('GeneratedCodeFunctionReuse/SS1','RTWSystemCode','Nonreusable function') set_param('GeneratedCodeFunctionReuse/SS2','RTWSystemCode','Nonreusable function') set_param('GeneratedCodeFunctionReuse/SS2','RTWFcnName','myfun2')
Generate and inspect the code.
slbuild(model)
### Starting build procedure for: GeneratedCodeFunctionReuse ### Successful completion of build procedure for: GeneratedCodeFunctionReuse Build Summary Top model targets: Model Build Reason Status Build Duration ========================================================================================================= GeneratedCodeFunctionReuse Generated code was out of date. Code generated and compiled. 0h 0m 8.3003s 1 of 1 models built (0 models already up to date) Build duration: 0h 0m 9.1906s
cfile=fullfile(pwd, 'GeneratedCodeFunctionReuse_grt_rtw', 'GeneratedCodeFunctionReuse.c'); coder.example.extractLines(cfile, '/* Model step', '/* Model initialize', 1, 0);
/* Model step function */ void GeneratedCodeFunctionReuse_step(void) { /* Outputs for Atomic SubSystem: '<Root>/SS1' */ myfun(); /* End of Outputs for SubSystem: '<Root>/SS1' */ /* Outputs for Atomic SubSystem: '<Root>/SS2' */ myfun2(); /* End of Outputs for SubSystem: '<Root>/SS2' */ }
The model step function contains calls to the functions myfun
and myfun2
. These functions have a void-void interface.
Change the Function Packaging parameter to Auto
.
set_param('GeneratedCodeFunctionReuse/SS1','RTWSystemCode','Auto') set_param('GeneratedCodeFunctionReuse/SS2','RTWSystemCode','Auto')
For the auto
setting, Simulink Coder chooses the optimal format. For this model, the optimal format is a reusable function.