羅 驍 王庭有 張才勇
(昆明理工大學機電工程學院)
昆明理工大學機電工程學院張才勇設計搭建的小微型嵌入式PLC 以STM32MCU 為CPU的核心硬件,采用層疊式設計,由3 塊PCB 板疊加構成。 頂層PCB 板為整個PLC 的核心板塊,集成MCU 芯片、EEPROM 芯片、485 通信接口和輸入輸出提示燈。 二層PCB 板為PLC 與控制對象的輸入輸出交流層,包含光耦輸入、繼電器輸入等外設元件。 底層PCB 板是PLC 的電源層,集成了交流轉直流的多個降壓模塊,可為PLC 和外接模塊供電。該小微型嵌入式PLC 的特點在于有極強的通用性和定制性,用戶可以根據自身需求的不同, 對PLC 的核心板進行裁剪或添加外設,即可在不同控制情景下實現用途。
目前, 小微型PLC 具有較高的市場占有率,并以其較高的性價比逐漸替代傳統小型PLC 設備,相比于現有的整塊式PLC,開發層疊結構的PLC 擴展性更好、更靈活。 因此筆者對層疊結構的小微型嵌入式PLC 上下位機指令一致性進行研究,并設計實驗驗證指令的實現情況。
根據國際電工委員會制定的工業控制編程語言標準IEC 1131-3,PLC 的編程語言包括以下5 種:梯形圖語言(LD)、指令表語言(IL)、功能模塊圖語言(FBD)、順序功能流程圖語言(SFC)和結構化文本語言(ST)[1]。其中,指令表語言是與匯編語言類似的一種助記符編程語言,和匯編語言一樣由操作碼和操作數組成。 在無計算機的情況下,適合采用PLC 手持編程器對用戶程序進行編制。 同時,指令表語言與梯形圖語言一一對應,在PLC 編程軟件下可以相互轉換[2]。
由于其他編程語言編寫的控制程序最終都需要轉換為指令序列來執行,并且利用指令表語言編寫的程序通常可以以最高速度運行[3~5],因此筆者選擇指令表語言作為PLC 編程軟件使用的編程語言。
1.2.1 基本邏輯運算
PLC 中最基本的運算方式是邏輯運算,基本邏輯運算包含“與”、“或”、“非”3 種運算,其余的邏輯運算均以此為基礎實現,因此首先要實現基本邏輯運算(圖1)。
1.2.2 邏輯堆棧
邏輯堆棧是PLC 在進行邏輯運算時用于存儲運算結果和中間值的區域, 是PLC 運行的基礎,一般采用整段連續的區域作為邏輯堆棧[6]。棧深關系到PLC 的運算能力,將PLC 的邏輯堆棧棧深和指針定義如下:

圖1 基本邏輯運算定義

上述代碼定義了邏輯堆棧的棧深為40,頂層作為運算結果的存儲區, 余下39 層用于存儲運算的中間值。 使用棧頂指針logical_array_pointer操作堆棧,當有數據入棧時,丟棄底層數據,將堆棧內容依次下移,騰空棧頂單元壓入數據;當有數據出棧時,彈出頂層數據,將堆棧內容依次上移,棧底單元補0。
定義邏輯堆棧后,需要PLC 來實現對堆棧的操作,因此要定義操作堆棧的指令,如圖2 所示。

圖2 部分堆棧操作指令定義
為了保證PLC 嚴格按照所編指令進行工作,需要將PLC 能夠識別的數字編碼與編程軟件所用的操作碼和操作數一一對應起來,表1 給出了部分操作碼和操作數對應的編碼。 將表1 所示的操作碼(操作數)對應的編碼寫入文件ins.m 中,并加入MATLAB,以保證編寫出的PLC 指令能夠正確編譯。

表1 部分操作碼和操作數對應的編碼
PLC 要執行指令, 首先需要識別指令函數,具體實現方法為:每當執行完任一指令后,指向用戶程序存儲區的指針會根據本條指令的占用內存自動向下偏移m(m=1,3,6)個字節,以達到正確取址和執行下一條指令的目的。 例如執行只有操作碼的LPS 指令,執行指令后指針向下偏移1 個字節, 繼續執行下一條指令。 若執行OUT Q0 指令, 操作碼OUT 占1 個字節,Q0 占2 個字節,則執行該指令后指針向下偏移3 個字節。 然后編寫ins_exc.c 文件,在其中定義用戶程序執行函數user_pro_exc (), 該函數的執行流程如圖3所示。

圖3 user_pro_exc()函數執行流程
如圖3 所示,執行user_pro_exc()函數時,首先判斷用戶程序存儲區內是否有用戶程序,如果用戶程序指針user_pro_storage_p 指向的地址內容為0,則說明沒有用戶程序,結束函數執行;反之,如果不為0,則執行construction()函數,該函數的執行流程如圖4 所示。

圖4 construction()函數執行流程
如圖4 所示,開始執行construction()函數后,首先執行選擇函數select()對用戶程序中的指令進行選擇,對于沒有操作數的指令,如LPS 指令等直接執行后即結束該函數。 對于既有操作碼又有操作數的指令, 如LD I0 指令等進一步匹配到sub_select()函數后再執行操作,sub_select()函數能為這些指令提供I、Q、M、C、T 等操作數。
完成PLC 對函數指令的識別工作后,即可達到使PLC 正確執行上位機用戶程序指令的目的。
使用MATLAB GUI 工具設計簡單的編程界面(圖5),實現PLC 程序的編程、編譯和下載功能。 該編程軟件界面左側為STL 指令編寫區域,在此區域內編寫所需的用戶程序;右側是編譯提示區域, 當指令編寫完成后點擊編譯按鈕,編譯提示區域會顯示編譯后的十六進制數。

圖5 PLC 編程軟件界面
設計實驗對PLC 的邏輯指令進行驗證,實驗指令包括:觸點指令LD、A、O、LDN、AN、ON;邏輯堆棧指令ALD、OLD、LPS、LRD、LPP; 輸出指令OUT。
在PC 端的PLC 編程軟件中輸入指令表指令,編譯如圖6 所示。

圖6 PLC 指令
在4 個輸出端口上各連接一個LED,當輸出端口得電時二極管發光,輸出端口不得電時二極管熄滅。
該實驗中設計多種接通方案, 具體如下:僅I0 或I3 得電時,Q3 得電,其余回路不接通。 I0 和I2 得電時,僅Q3 得電,其余回路不接通;若同時再接通I4、I5 或I6,則在Q3 保持燈亮的情況下,分別有Q0、Q1 或Q2 燈亮,說明串聯電路接通。I0和I3 得電時的情況與I0 和I2 得電情況一致。
通過實驗,觀察到如下現象:
a. 啟動PLC,按下I0,Q3 得電,對應的LED點亮,其余LED 保持熄滅;斷開I0,按下I3,Q3得電,對應的LED 點亮,其余LED 保持熄滅。
b. 接通I0 和I2 的同時,再按下I4,Q3 和Q0得電,對應的LED 點亮;斷開I4,接通I5,Q3 和Q1 得電,對應的LED 點亮,其余LED 保持熄滅;斷開I5,接通I6,Q3 和Q2 得電,對應的LED 點亮,其余LED 保持熄滅。
c. 接通I0 和I3 的同時,再按下I4,Q3 和Q0得電,對應的LED 點亮;斷開I4,接通I5,Q3 和Q1 得電,對應的LED 點亮,其余LED 保持熄滅;斷開I5,接通I6,Q3 和Q2 得電,對應的LED 點亮,其余LED 保持熄滅。
綜上所述,實驗結果與設計方案一致,說明使用筆者設計的指令表語言編程器編寫的用戶指令在下位機PLC 中得到了正確執行。
筆者使用MATLAB 編寫出的PLC 指令表語言編程軟件能夠正確進行指令的編譯,并且能夠在STM32MCU 的下位機PLC 上正確執行, 說明上位機和下位機的指令具有一致性,是一個能實際應用的編程軟件。