This article uses Berghof’s B-Nimis MC-Pi Plus Controller and the CAA.File library to list the File and Folder installed on the USB stick.
Let’s enjoy FA.

Reference Video
Codesys.Let’s List-up the items in an USB Directory!
Foreword
Thank you from the bottom of my heart for visiting my technical blog and YouTube channel.
We are currently running the “Takahashi Chris” radio show with Full-san (full@桜 八重 (@fulhause) / X) which I deliver every Wednesday night.
Currently, our activities continue almost free of charge, and your warm support is very important for us to provide more content.If you are able, we would be very happy if you could support us by clicking on the links below.
Membership of Takahashi Chris
You can sign up for a membership to the radio we are doing with MR.Full (full@桜 八重 (@fulhause) / X from here.
https://note.com/fulhause/membership/join
AMAZON Gift List
This will be of great use to me in creating content for my blog and improving my facilities.
https://www.amazon.co.jp/hz/wishlist/ls/H7W3RRD7C5QG?ref_=wl_share
Patreon
Here is a small Patreon of support for the creation of content and equipment for my blog.
https://www.patreon.com/user?u=84249391
Your support will help us to enhance our activities.
Thank you in advance for your support.
Email Address(*=@)
X
CAA.File
This is the library CAA.File used in this article.
FILE_DIR_ENTRY
This data structure holds information on directory entries.
Variables | Type | Description |
sEntry | CAA.FILENAME | Directory or file name |
szSize | CAA.SIZE | file size |
xDirectory | BOOL | TRUE: DirectoryFALSE: File |
xExclusive | BOOL | TRUE: exclusive Access modeFALSE: Multiple access modes possible. |
dtLastModification | DT | Last update datee.g.2006-05-08-00:00:00 |
DirList
The FB reads the directory entry and the information is written to the structure “deDirEntry” of type “FILE_DIR_ENTRY”. Then, if the FB cannot find any more entries, the error message “ERROR.NO_MORE_ENTRIES” is generated and the entry in the structure “deDirEntry” is deleted.
VAR_INPUT
Variables | Type | Description |
xExecute | BOOL | Rising edge: Start of operationFalling edge: output reset |
hDir | CAA.HANDLE | directory handle |
VAR_OUTPUT
Variables | Type | Description |
xDone | BOOL | Action successfully executed. |
xBusy | BOOL | TRUE=FB running |
xError | BOOL | TRUE=FB error |
eError | ERROR | Local library error ID(5106-FILE_NO_MORE_ENTRIES: no further entries) |
deDirEntry | FILE_DIR_ENTRY | directory entry |
DirOpen
This FB opens the specified directory.
VAR_INPUT
Variables | Type | Description |
xExecute | BOOL | Rising edge: Start of operationFalling edge: output reset |
sDirName | CAA.FILENAME | Directory name, absolute or relative path specification |
VAR_OUTPUT
Variables | Type | Description |
xDone | BOOL | Action successfully executed. |
xBusy | BOOL | TRUE=FB running. |
xError | BOOL | TRUE = FB error |
eError | ERROR | Local library error ID(5106-FILE_NO_MORE_ENTRIES: no further entries) |
hDir | CAA.HANDLE | directory handle |
DirClose
This FB closes access to the specified directory.
VAR_INPUT
Variables | Type | Description |
xExecute | BOOL | Rising edge: Start of operationFalling edge: output reset |
hDir | CAA.HANDLE | directory handle |
VAR_OUTPUT
Variables | Type | Description |
xDone | BOOL | Action successfully executed. |
xBusy | BOOL | TRUE=FB running. |
xError | BOOL | TRUE = FB error |
eError | ERROR | Local library error ID(5106-FILE_NO_MORE_ENTRIES: no further entries) |
Implementation
Enable SSH Server
To enable the Berghof Controller’s SSH Server, go to Webserver > SSH Server > Enabled.
Check the USB
Access SSH using the Berghof Controller and use the lssub command to Check if the USB is recognised.
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:~ |
Next, use the ls command to list-up the Files in the USB.
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
Import the CAA File and CAA Types libraries to Codesys into the project.
GVL – gUSBFileList
Create a Global Variables List.
- stFileDirEntry stores the Directory/File information obtained when DirList FB is executed.
- diMaxIndex is the maximum validation Index
- xSearch=TRUE starts a search.
{attribute ‘qualified_only’} VAR_GLOBAL stFileDirEntry:ARRAY[0..99]OF FILE.FILE_DIR_ENTRY; diMaxIndex:INT:=19; xSearch:BOOL; END_VAR |
MAIN
This is the Flow of this MAIN program.
First, initialise all FBs, open Directory> and list the Items in it.Then there is a Counter in the Step Flow, which is always compared to the Max Counter (you could list up infinitely, but it is not very practical).
- If the current Counter is less than the MaxCount setting, then ListUP the next item.
- If the current Counter is greater than the MaxCount setting, >END
- If File/Directory not found > End

VAR
This is the variable definition of the program.
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
This is the program created for the Flow mentioned earlier.
//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
To create a Codesys screen, add a Table Object.
Specify the array data to be displayed in the Properties of the Data array.
Done!The final step is to create a Search button and link it to the GVL xSearch button.
Login
Download the program to the CPU.
Result
By clicking on the Search button, all Folders and Files in the relevant Directory can be listed and displayed on the Codesys screen.
You can Download the project File from this Link.
https://github.com/soup01Threes/Codesys/blob/main/Berghof-ListupFile.projectarchive