本文描述通過通過Stateflow調用外部C代碼調用外部C代碼的方法。
1 問題引入
情形1:在汽車嵌入式軟件開發的過程中,通常是用模型生成代碼的方式開發應用層軟件,用手寫代碼的方式開發底層軟件和接口函數。應用層經常需要調用到底層的函數,比如應用層通過接口函數獲取底層的變量值。
情形2:很多早期的項目沒有引入MBD(基於模型的設計),而是全部通過手寫代碼完成。等到後面採用模型生成代碼的時候,也會想要調用以前開發的成熟的代碼。
以上兩種情況,都需要通過在Simulink模型中調用外部的C代碼。一種方法是通過S-function封裝來實現,但是比較麻煩。本文介紹通過Stateflow實現調用外部C代碼。
2 調用外部C代碼的過程
2.1 準備外部文件
想要調用外部C代碼,首先得要在Matlab路徑下能找到這個C代碼所在的文件。如果暫時沒有開發也沒關係,可以建立一個空殼代碼,先“騙一下”Matlab。
如圖所示,在Matlab當前路徑下建立兩個文件:myfile.c和myfile.h:
在myfile.c中寫入代碼:
#include "myfile.h"
void HandCode(void)
{
}
在myfile.h中寫入代碼:
void HandCode(void);
可以看到,HandCode()這個函數沒有參數也沒有返回值,而且裏面是空的,啥都沒有。
2.2 搭建模型
1.新建一個空白Simulink,建立一個Chart。
2.點擊去這個Chart,打開Model Explorer,將Action Language設置爲C。
3.建立一個簡單的流程圖,並在圓括號的動作中寫上之前的那個HandCode的C代碼。
3.打開設置——Simulation Target,填寫右側的Source file和Header file並確定。
2.3 生成代碼
Ctrl+B生成代碼,在打開的報告中就可以看到step函數中調用了這個C代碼,以及頭文件中包含了myfile.h。
最後別忘了,集成的時候要把真正的外部調用代碼拿來編譯,而不是我們自己建立的空殼代碼。
3 調用有參數和返回的函數
上面舉的例子是沒有參數和返回值的,對於有參數和返回值的函數也是可以調用的。
1.首先修改一下C代碼,加上參數和返回。
C文件:
#include "myfile.h"
single HandCode(single Input1)
{
}
頭文件:
typedef float single;
single HandCode(single Input1);
這裏用typedef定義一個single類型。
2.重新打開Chart,加上輸入輸出參數,定義好Name,Scope和Datatype,注意Datatype保持和代碼中一致。
此時,Chart外面就會多出兩個輸入輸出口,連接上Inport和Outport。
3.Ctrl+B生成代碼,就會生成調用了參數的代碼。
4 總結
通過Stateflow調用外部C代碼是一種很方便的方法。不過在2018b以後的版本,推出了C Caller的模塊可以調用外部C代碼。