前言
上一篇文章讲到如何设置simulink code,simulink code 交换两个变量的值,使生成的代码和手写代码完全一致;那么本篇文章就演示,如何调用别人给你的算法函数;调用函数就使用上一篇文章生成的函数:
函数原型:
extern void Exchange(float *a, float *b);
生成的算法文件如下:
copy.c:
#include "copy.h"
/* Model step function */
void Exchange(float *a, float *b)
{
float c;
/* DataStoreWrite: '<Root>/Data Store Write1' */
c = *a;
/* Outport: '<Root>/Out1' incorporates:
* DataStoreRead: '<Root>/Data Store Read'
* DataStoreWrite: '<Root>/Data Store Write'
*/
*a = *b;
/* Outport: '<Root>/Out2' incorporates:
* DataStoreRead: '<Root>/Data Store Read1'
*/
*b = c;
}
/* Model initialize function */
void copy_initialize(void)
{
/* (no initialization code required) */
}
/*
* File trailer for generated code.
*
* [EOF]
*/
copy.h
#ifndef RTW_HEADER_copy_h_
#define RTW_HEADER_copy_h_
#ifndef copy_COMMON_INCLUDES_
#define copy_COMMON_INCLUDES_
#include <stdbool.h>
#include <stdint.h>
#endif /* copy_COMMON_INCLUDES_ */
/* Model entry point functions */
extern void copy_initialize(void);
/* Customized model step function */
extern void Exchange(float *a, float *b);
#endif
Simulink 调用 C caller
-
创建一个callC模型;添加如下模块:constant; c Function; display
-
把准备好的文件添加到模型
模型文件夹:分别为上次生成的两个文件,用于交换两个变量的值;
模型设置:把文件名,路径添加到模型设置中
打开设置 ——仿真目标;首先填写源文件:原文件名copy.c;其次在包含目录srec;包含头文件#include “copy.h”;
注意:这个顺序很重要,包含目录要填写相对路径和绝对路径,如果文件在当前目录可以不用填写,如果有多个目录中间用空格隔开;包含头文件时,可以点击“基于源文件自动填充”,则会根据源文件中的定义和文件目录自动填写头文件。
- 选择C Caller 函数
点击更新按钮,在下拉菜单中选择Exchange函数;
端口类型根据函数定义自动识别;也可以根据需要修改。
- 仿真结果如下:
输入值发生了值的交换。
- 查看生成代码
定义了两个结构体全局变量,
Extu rtu:外部输入全局变量,类型是结构体;
Exty rty:外部输出全局变量,类型是结构体;
很明显可以看出:调用了函数Exchange(&rtb_CCaller_o1, &rtb_CCaller_o2); 完成了值的交换。
/* External inputs (root inport signals with default storage) */
ExtU rtU;
/* External outputs (root outports fed by signals with default storage) */
ExtY rtY;
/* Model step function */
void callC_step(void)
{
real32_T rtb_CCaller_o1;
real32_T rtb_CCaller_o2;
/* CCaller: '<Root>/C Caller' incorporates:
* Inport: '<Root>/In1'
* Inport: '<Root>/In2'
* Sum: '<Root>/Sum'
*/
rtb_CCaller_o1 = rtU.In1 + rtU.In2;
rtb_CCaller_o2 = rtU.In1;
Exchange(&rtb_CCaller_o1, &rtb_CCaller_o2);
/* Outport: '<Root>/Out1' */
rtY.Out1 = rtb_CCaller_o1;
/* Outport: '<Root>/Out2' */
rtY.Out2 = rtb_CCaller_o2;
}
VS code 调用
下面演示如何在c 中调用我们用simulink生成的交换值的函数;simulink code交换两个变量的值
1新建一个文件夹;2把文件copy.h,copy.c拷贝到这个文件夹;3右键以vscode打开文件夹;
4添加新文件demo.c,输入一下代码;5配置编译器,任务文件,调试文件,多文件编译;6终端里选择“运行任务”,生成demo.exe文件;7命令行输入:demo.exe,打印输出
结果显示,a,b的值发生了交换。说明simulink生成的算法函数能够被直接调用。
结论
通过以上的例子表明:simulink code生成的算法不仅可以被自己调用,也可以被外部集成;摆脱开发环境的限制。算法工程师专注于仿真,把测试好的算法模型生成code,交给项目工程师集成编译。别人好的算法code也可以集成到模型测试,并生成统一的算法。