CODESYS Example Projectを調べてみた#8 (Trace)
Trace
今回は、Trace
について調べました。このExampleでは、CmpTraceMgr
というライブラリを使用しています。CmpTraceMgr
は、IECプログラムやランタイムシステムコンポーネント、Editor上のTraceに関連するパケット(レコードの入れ物)とレコード(監視したい変数)を制御できます。
セットアップ
まずはExampleコードをダウンロードし、デバイスをアップデートします。私の環境(CODESYS V3.5 SP20 Patch2)ではライブラリが不足していたため、以下のボタンから追加することでビルドできました。
プログラムの内容
Exampleには、TraceRecordingExample
とIECTraceConfiguration
という2つのアプリケーションが含まれています。
-
TraceRecordingExample
: 視覚的なTraceの設定を行う例 -
IECTraceConfiguration
: STコードからCmpTraceMgr
を利用する例
それぞれの中身を確認していきましょう。
TraceRecordingExample
PLC_PRG(PRG)内では、GEN FBを使ってSIN波形、TRIANGLE波形、RECTANGLE波形の3種類を生成し、iSignal1、iSignal2、iSignal3に出力しています。GEN FBは、Utilライブラリ内のSignalsに含まれています。
PROGRAM PLC_PRG
VAR
generator1 : GEN;
iSignal1 : INT;
generator2 : GEN;
iSignal2 : INT;
generator3 : GEN;
iSignal3 : INT;
// Starts the trace recording
xStartVisuTraceTrigger : BOOL;
END_VAR
// Generate three signals
generator1(MODE := GEN_MODE.SINE, BASE := TRUE, PERIOD := TIME#500MS, AMPLITUDE := 500, OUT => iSignal1);
generator2(MODE := GEN_MODE.TRIANGLE, BASE := TRUE, PERIOD := TIME#2000MS, AMPLITUDE := 200, OUT => iSignal2);
generator3(MODE := GEN_MODE.RECTANGLE, BASE := TRUE, PERIOD := TIME#300MS, AMPLITUDE := 1000, OUT => iSignal3);
生成したiSignal1、iSignal2、iSignal3の値は、WebVisuのTraceWidgetで表示します。
Application内のTrace
を選択し、Configuration
をクリックすると「Trace Configuration」画面が表示されます。左側のTrace Record
を選択すると「Record Settings」を変更できます。オシロスコープを操作するような感覚で設定できそうです。
Trace
以下にあるPLC_PRG.iSignal1,2,3
を選択すると、変数の設定を行えます。Variable
と表示されているプルダウンメニューをParameter
に切り替えると、system parameterも記録できるようです。ただしOnline Helpによると、CmpTraceMgr
コンポーネントが必要とのことです。
TraceVisuの画面でTraceWidgetを選択すると、Visualization_Trace1
という名前のTraceが作成されています。先ほど直接設定したTraceとは別物のようですが、設定内容はほぼ同じです。
「Display Settings」ボタンを押すと、X軸・Y軸の設定画面が表示されます。
「Advanced」ボタンを押すと、サンプリング周期の設定が可能です。
また、「Copy from Trace」ボタンを押すと、Trace Instanceの内容がコピーされます。
TraceVisu画面には、トリガ用ボタンや保存ボタン、保存ファイル名入力フォームが用意されています。Online Helpによると、これらはInsert Elements for Controlling Trace
で追加されるようです。Windows上のDeviceにプログラムをダウンロードして「Store」を実行してみましたが、正しく動作しなかったため、CODESYSControl.cnf
などで追加設定が必要なのかもしれません。
IECTraceConfiguration
2つ目のアプリケーションは、CmpTraceMgr
を使ってTraceのレコードやパケットを制御する例です。パケットはトレース全体の入れ物であり、サンプリング周期やバッファサイズなどを設定します。レコードは、パケットが記録する具体的な変数とその属性を管理します。
サンプルコードでは、xStart
をトリガにパケットを作成し、その後にレコード(iSignal)を追加してトレースを開始します。アプリケーションに含まれるTraceオブジェクト(Trace1)は、以下のような設定になっています。
サンプルプログラムは次のとおりです。
PROGRAM PLC_PRG
VAR
xStart : BOOL := TRUE;
xStop : BOOL := FALSE;
iSignal : INT; // The signal to record
fbTraceManager : FBTraceMgr;
PacketConfig : TracePacketConfiguration;
hPacket1 : CmpTraceMgr.RTS_IEC_HANDLE;
RecordConfig : TraceRecordConfiguration;
hRecord1 : CmpTraceMgr.RTS_IEC_HANDLE;
pApp : POINTER TO APPLICATION;
xError : BOOL;
generator1 : GEN;
END_VAR
IF xStart THEN
// パケットの設定
PacketConfig.pszName := ADR('IECTraceConfiguration.Trace1'); // Name of trace
PacketConfig.pszApplicationName := ADR('IECTraceConfiguration');
PacketConfig.pszIecTaskName := ADR('Task'); // Name of the task
PacketConfig.pszComment := ADR('Demo packet');
PacketConfig.ulEveryNCycles := 1;
PacketConfig.ulBufferEntries := 1000;
PacketConfig.ulFlags := TRACE_PACKET_FLAGS.TRACE_PACKET_FLAGS_TIMESTAMP_MS AND TRACE_PACKET_FLAGS.TRACE_PACKET_FLAGS_AUTOSTART;
// CreatePacket()で上記の設定に従いパケットを作成
IF (NOT fbTraceManager.CreatePacket(PacketConfig := PacketConfig, hPacket => hPacket1)) THEN
xError := TRUE;
END_IF
// レコードの設定
RecordConfig.pszVariable := ADR('iSignal');
RecordConfig.tcClass := INT_TO_UDINT(TypeClass.TYPE_INT);
RecordConfig.ulSize := SIZEOF(iSignal);
pApp := AppFindApplicationByName('IECTraceConfiguration', 0);
AppGetAreaOffsetByAddress(pApp, ADR(iSignal), ADR(RecordConfig.tvaAddress.taAddress.Area.usArea), ADR(RecordConfig.tvaAddress.taAddress.Area.ulOffset));
RecordConfig.tvaAddress.ulAddressFlags := TRACE_VAR_ADDRESS_FLAGS_IEC OR TRACE_VAR_ADDRESS_FLAGS_AREA_OFFSET;
RecordConfig.ulGraphColor := 16#FF00FF00; // green
RecordConfig.ulGraphType := 1; // Line with points
// 警告範囲と色の設定
RecordConfig.fCriticalLowerLimit := -90;
RecordConfig.fCriticalUpperLimit := 90;
RecordConfig.bActivateMinWarning := TRUE;
RecordConfig.bActivateMaxWarning := TRUE;
RecordConfig.ulMinWarningColor := 16#FFFF0000; // red
RecordConfig.ulMaxWarningColor := 16#FF0000FF; // blue
// AddRecord()でレコードをパケットに追加
IF (NOT fbTraceManager.AddRecord(RecordConfig := RecordConfig, hPacket := hPacket1, hRecord => hRecord1)) THEN
xError := TRUE;
END_IF
// StartPacket()でパケットを開始
IF (NOT fbTraceManager.StartPacket(hPacket := hPacket1)) THEN
xError := TRUE;
END_IF
xStart := FALSE;
END_IF
IF xStop THEN
// StopPacket()でパケットを停止
IF (NOT fbTraceManager.StopPacket(hPacket := hPacket1)) THEN
xError := TRUE;
END_IF
xStop := FALSE;
END_IF
// Generate a sine signal
generator1(MODE := GEN_MODE.SINE, BASE := TRUE, PERIOD := TIME#5000MS, AMPLITUDE := 100, OUT => iSignal);
このプログラムでは、FBTraceMgr
というFB(ファンクションブロック)を介してTrace Managerの機能を呼び出しています。CreatePacket()
, AddRecord()
, StartPacket()
, StopPacket()
などのメソッドがあらかじめ実装されているので、生のCmpTraceMgr
よりも扱いやすい形となっています。
FUNCTION_BLOCK FBTraceMgr
VAR_INPUT
END_VAR
VAR_OUTPUT
END_VAR
VAR
_lastError : UDINT;
_hPacket : CmpTraceMgr.RTS_IEC_HANDLE;
_hRecord : CmpTraceMgr.RTS_IEC_HANDLE;
END_VAR
METHOD CreatePacket : BOOL
VAR_INPUT
PacketConfig : TracePacketConfiguration;
END_VAR
VAR_OUTPUT
hPacket : CmpTraceMgr.RTS_IEC_HANDLE;
END_VAR
hPacket := TraceMgrPacketCreate(PacketConfig, _lastError);
IF hPacket <> CmpTraceMgr.RTS_INVALID_HANDLE THEN
// Complete the trace packet
TraceMgrPacketComplete(hPacket);
CreatePacket := TRUE;
RETURN;
END_IF
CreatePacket := FALSE;
METHOD AddRecord : BOOL
VAR_INPUT
RecordConfig : TraceRecordConfiguration;
hPacket : CmpTraceMgr.RTS_IEC_HANDLE;
END_VAR
VAR_OUTPUT
hRecord : CmpTraceMgr.RTS_IEC_HANDLE;
END_VAR
hRecord := TraceMgrRecordAdd(hPacket, RecordConfig, _lastError);
IF hRecord <> CmpTraceMgr.RTS_INVALID_HANDLE THEN
TraceMgrPacketComplete(hPacket);
AddRecord := TRUE;
RETURN;
END_IF
AddRecord := FALSE;
その他のメソッドについては、Exampleコード本体を参照してください。
気づきと学び
- 信号処理や数値処理でよく使う機能は、Utilライブラリを探すと見つかるかもしれません。
- Traceでは、変数のリアルタイム表示だけでなく、Store/Load機能や統計的処理も可能です。
まとめ
- Traceはオシロスコープのように信号の追加やトリガー設定が行えます。
- ST内でTraceを制御したい場合は、
CmpTraceMgr
を利用します。ライブラリ活用のポイントは以下のとおりです。-
TraceMgrPacketCreate
でトレースの“枠”を作り、周期やバッファ数、フラグを設定する。 -
TraceMgrRecordAdd
で記録したい変数・型・アドレスを指定し、可視化のグラフ設定や警告値を設定する。 -
TraceMgrPacketStart
/TraceMgrPacketStop
でトレースのオン/オフを制御する。
-
Discussion