今回の記事ではBerghofのB-Nimis MC-Pi Plus ControllerとCAA.Fileライブラリを使用し、USB メモリにインストールされているFileとFolderをリストアップします。
さ、FAを楽しもう。
CAA.File
こちらは今回記事で使用するライブラリCAA.Fileです。
FILE_DIR_ENTRY
このデータ構造は、ディレクトリエントリの情報を保持します。
Variables | Type | Description |
sEntry | CAA.FILENAME | ディレクトリ名またはファイル名 |
szSize | CAA.SIZE | ファイルサイズ |
xDirectory | BOOL | TRUE: ディレクトリFALSE: ファイル |
xExclusive | BOOL | TRUE: exclusive アクセスモードFALSE: 複数アクセスモード可能 |
dtLastModification | DT | 最終更新日時e.g.2006-05-08-00:00:00 |
DirList
このFBはディレクトリエントリを読み込み、その 情報は “FILE_DIR_ENTRY “型の構造体 “deDirEntry “に書き込まれます。 そして、FBがそれ以上のエントリを見つけられない場合、エラーメッセージ “ERROR.NO_MORE_ENTRIES “が生成され、構造体 “deDirEntry “のエントリが削除されます。
VAR_INPUT
Variables | Type | Description |
xExecute | BOOL | 立ち上がりエッジ: 動作開始立ち下がりエッジ: 出力リセット |
hDir | CAA.HANDLE | ディレクトリハンドル |
VAR_OUTPUT
Variables | Type | Description |
xDone | BOOL | アクションは実行成功 |
xBusy | BOOL | TRUE=FB実行中 |
xError | BOOL | TRUE=FBエラー |
eError | ERROR | ローカル・ライブラリ・エラーID (5106‐FILE_NO_MORE_ENTRIES: これ以上のエントリはありません) |
deDirEntry | FILE_DIR_ENTRY | ディレクトリエントリ |
DirOpen
このFBは指定されたディレクトリを開けます。
VAR_INPUT
Variables | Type | Description |
xExecute | BOOL | 立ち上がりエッジ: 動作開始立ち下がりエッジ: 出力リセット |
sDirName | CAA.FILENAME | ディレクトリ名、絶対パスまたは相対パス指定 |
VAR_OUTPUT
Variables | Type | Description |
xDone | BOOL | アクションは実行成功 |
xBusy | BOOL | TRUE=FB実行中 |
xError | BOOL | TRUE=FBエラー |
eError | ERROR | ローカル・ライブラリ・エラーID (5106‐FILE_NO_MORE_ENTRIES: これ以上のエントリはありません) |
hDir | CAA.HANDLE | ディレクトリハンドル |
DirClose
このFBは、指定されたディレクトリへのアクセスをクローズする。
VAR_INPUT
Variables | Type | Description |
xExecute | BOOL | 立ち上がりエッジ: 動作開始立ち下がりエッジ: 出力リセット |
hDir | CAA.HANDLE | ディレクトリハンドル |
VAR_OUTPUT
Variables | Type | Description |
xDone | BOOL | アクションは実行成功 |
xBusy | BOOL | TRUE=FB実行中 |
xError | BOOL | TRUE=FBエラー |
eError | ERROR | ローカル・ライブラリ・エラーID (5106‐FILE_NO_MORE_ENTRIES: これ以上のエントリはありません) |
Implementation
Enable SSH Server
Berghof ControllerのSSH Serverを有効にするため、Webserverアクセスし>SSH Server>Enabledしてるかを確認してください。
Check the USB
BerghofのControllerを使ってSSHにアクセスし、lssub コマンドでUSBが認識されたかをCheckしてください。
ssh root@192.168.0.40 root@S-01030303-0100-00116:~ lsusb Bus 001 Device 003: ID 0424:9e00 Standard Microsystems Corp. Bus 003 Device 002: ID 0424:9e00 Standard Microsystems Corp. Bus 001 Device 005: ID 0424:2240 Standard Microsystems Corp. Bus 001 Device 004: ID 0403:6015 Future Technology Devices International, Ltd Bridge(I2C/SPI/UART/FIFO) Bus 002 Device 002: ID 0424:5744 Standard Microsystems Corp. Bus 001 Device 006: ID 0424:2740 Standard Microsystems Corp. Bus 001 Device 002: ID 0424:2744 Standard Microsystems Corp. Bus 001 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub Bus 003 Device 001: ID 1d6b:0002 Linux Foundation 2.0 root hub Bus 002 Device 004: ID 058f:6387 Alcor Micro Corp. Flash Drive Bus 002 Device 001: ID 1d6b:0003 Linux Foundation 3.0 root hub root@S-01030303-0100-00116:~ |
次はls コマンドでUSB内のFileをList-upしてみましょう。
root@S-01030303-0100-00116:~ cd /media/usb1/ root@S-01030303-0100-00116:/media/usb1 ls 20241217171509RN070656411JP4WTRLRhl9142b8dcbe7d7958f743649d354428d4.pdf 20241218090205EN357413577JPc4ZRf5RV9142b8dcbe7d7958f743649d354428d4.pdf CreatefromCodesys System Volume Information tes2 test1.text |
Add Library
CodesysにCAA FileとCAA TypesライブラリをプロジェクトにImportします。
GVL – gUSBFileList
Global Variables Listを作成します。
- stFileDirEntryはDirList FBを実行したとき取得したDirectory・File情報を格納する
- diMaxIndexは最大検証Index
- xSearch=TRUEは検索開始する
{attribute ‘qualified_only’} VAR_GLOBAL stFileDirEntry:ARRAY[0..99]OF FILE.FILE_DIR_ENTRY; diMaxIndex:INT:=19; xSearch:BOOL; END_VAR |
MAIN
こちらは今回のMAINプログラムのFlowになります。
まずはすべてのFBを初期化し、Directoryを開き>中のItemをリストアップします。そしてStep FlowにCounterがありまして、常にMax Counterと比較しています(無限にListアップしてもよいですが、あまり現実的ではないので)。
- もし現在CounterがMaxCountの設定より小さいなら>次はのItemをListUPする
- もし現在CounterがMaxCountの設定より大きいなら>終わり
- もしFile/Directoryが見つからない>終わり
VAR
こちらはプログラムの変数定義です。
PROGRAM pTest2 VAR dirHandle : CAA.HANDLE; FB_DirList : FILE.DirList ; FB_DirOpen : FILE.DirOpen; FB_DirClose : FILE.DirClose; xExecute :BOOL; xClose :BOOL; xList :BOOL; xSearch :BOOL; FB_TON :TON; R_TRIG_ListDone :R_TRIG; END_VAR VAR iStep :INT; iMaxCount :INT; iCounter :INT; iResetCounter :INT; END_VAR VAR CONSTANT ciStep00_Init :INT:=0; ciStep10_Open :INT:=10; ciStep20_List :INT:=20; ciStep25_List :INT:=25; ciStep30_Close :INT:=30; ciStep399_End :INT:=399; END_VAR |
Program
こちらは先程のFlowに合わせて作成したプログラムです。
//01.Start to search //02.List the data //02.1.Store to GVL //99.Close the Handle CASE iStep OF ciStep00_Init: iMaxCount:=gUSBFileList.diMaxIndex; xSearch:=gUSBFileList.xSearch AND iStep =0; xExecute:=FALSE; xList:=FALSE; xClose:=FALSE; iCounter:=0; IF NOT FB_DirClose.xBusy AND NOT FB_DirClose.xError AND NOT FB_DirList.xBusy AND NOT FB_DirList.xError AND NOT FB_DirOpen.xBusy AND NOT FB_DirOpen.xError AND xSearch THEN FOR iResetCounter:=0 TO iMaxCount DO gUSBFileList.stFileDirEntry[iResetCounter].dtLastModification:=DT#1970-1-1-0:0:0; gUSBFileList.stFileDirEntry[iResetCounter].sEntry:=”; gUSBFileList.stFileDirEntry[iResetCounter].szSize:=0; gUSBFileList.stFileDirEntry[iResetCounter].xDirectory:=FALSE; gUSBFileList.stFileDirEntry[iResetCounter].xExclusive:=FALSE; END_FOR FB_TON(IN:=TRUE,PT:=T#0.01S); IF FB_TON.Q THEN xSearch:=FALSE; iStep:=ciStep10_Open; FB_TON(IN:=FALSE); END_IF; END_IF ciStep10_Open: xExecute:=TRUE; IF NOT FB_DirOpen.xError AND FB_DirOpen.hDir <>0 THEN iStep:=ciStep20_List; END_IF ciStep20_List: xList:=TRUE; IF R_TRIG_ListDone.Q THEN gUSBFileList.stFileDirEntry[iCounter]:=FB_DirList.deDirEntry; iCounter:=iCounter+1; IF iCounter >= iMaxCount THEN iStep:=ciStep30_Close; ELSE iStep:=ciStep25_List; END_IF ELSIF FB_DirList.xError THEN iStep:=ciStep30_Close; END_IF ciStep25_List: xList:=FALSE; IF NOT FB_DirList.xDone THEN iStep:=ciStep20_List; END_IF ciStep30_Close: xClose:=TRUE; IF FB_DirClose.xDone THEN gUSBFileList.xSearch:=FALSE; iStep:=ciStep399_End; END_IF ciStep399_End: iStep:=ciStep00_Init; END_CASE R_TRIG_ListDone(CLK:=FB_DirList.xDone); FB_DirOpen( xExecute:=xExecute ,sDirName:=’/media/usb1′ ,hDir=>dirHandle ); FB_DirList( xExecute:=xList ,hDir:=dirHandle); FB_DirClose( xExecute:=xClose ,hDir:=dirHandle ); |
Visuilation
Codesysの画面を作成するため、Table Objectを追加します。
Data arrayのPropertiesに表示する配列データを指定します。
Done!最後はSearchボタンを作成し、GVLのxSearchボタンと紐つけます。
Login
プログラムをCPUにDownloadします。
Result
Searchボタンをクリックすれば、該当するDirectoryのすべてのFolderやFileをリストアップでき、Codesys画面に表示できます。
こちらはのLinkからプロジェクトFileをDownloadしてください。
https://github.com/soup01Threes/Codesys/blob/main/Berghof-ListupFile.projectarchive