FreeBSD 13/14/15: RTL dirent record mismatch (64-bit inodes) causes empty directory
<!-- See available text formatting: https://gitlab.com/help/user/markdown.md --> ## Summary FreeBSD 13/14: RTL dirent record mismatch (64-bit inodes) causes empty directory. I have identified a critical ABI mismatch in the Free Pascal RTL for FreeBSD versions 13, 14 and 15. When running applications on FreeBSD 14, directory listings (via FindFirst/FindNext or fpGetDirentries) return empty results because the RTL still uses the legacy 32-bit dirent structure. In FreeBSD 13+, the dirent structure was updated for 64-bit inodes (ino64):d_fileno (inode) is now 64-bit. An 8-byte d_off (directory offset) field was added.d_namlen is now 16-bit. Because FPC uses its own record definitions rather than the system's dirent.h, the data returned by the kernel is misaligned in Pascal applications. Request:Could the RTL be updated to detect the FreeBSD version and use the correct structure? Since there is no built-in FPC_FREEBSD_OSVERSION define, perhaps the RTL should be using a version check similar to how C headers use __FreeBSD_version. I have verified that manually patching the record to the following layout fixes the issue in mselibc.pas of MSEgui: ## System Information - **Operating system: Freebsd 13/14/15** - **Processor architecture:** x86, x86-64, ARM, AARCH64 - **Compiler version:** 3.2, 3.2.2, 3.2.3, 3.3, trunk - **Device:** Computer, Tablet ## Steps to reproduce ``` program test_dirent; uses BaseUnix, Errors; var dir: PDir; entry: pDirent; begin dir := fpOpenDir('.'); if dir = nil then begin writeln('Could not open directory.'); halt(1); end; writeln('Reading current directory...'); // On FreeBSD 13,14,15 this loop will typically fail to find names // because the RTL's dirent record offsets are incorrect. entry := fpReadDir(dir^); while entry <> nil do begin writeln('Found: ', entry^.d_name); entry := fpReadDir(dir^); end; fpCloseDir(dir^); end. ``` ## Example Project See what precedes. ## What is the current bug behavior? Empty directory. ## What is the expected (correct) behavior? See the files in directory. ## Relevant logs and/or screenshots <!-- Paste any relevant logs - please use code blocks (```) to format console output, logs, and code --> ## Possible fixes Valid for amd64, i386, and aarch64: ``` type dirent = record d_fileno: cuint64; d_off: clonglong; d_reclen: cuint16; d_type: cuint8; d_pad0: cuint8; d_namlen: cuint16; d_pad1: cuint16; d_name: array[0..255] of char; end; ```
issue