| 907 | } |
| 908 | |
| 909 | int __syscall_getdents64(int fd, void* dirp, size_t count) { |
| 910 | dirent* result = (dirent*)dirp; |
| 911 | |
| 912 | // Check if the result buffer is too small. |
| 913 | if (count / sizeof(dirent) == 0) { |
| 914 | return -EINVAL; |
| 915 | } |
| 916 | |
| 917 | auto openFile = wasmFS.getFileTable().locked().getEntry(fd); |
| 918 | if (!openFile) { |
| 919 | return -EBADF; |
| 920 | } |
| 921 | auto lockedOpenFile = openFile->locked(); |
| 922 | |
| 923 | auto dir = lockedOpenFile.getFile()->dynCast<Directory>(); |
| 924 | if (!dir) { |
| 925 | return -ENOTDIR; |
| 926 | } |
| 927 | auto lockedDir = dir->locked(); |
| 928 | |
| 929 | // A directory's position corresponds to the index in its entries vector. |
| 930 | int index = lockedOpenFile.getPosition(); |
| 931 | |
| 932 | // If this directory has been unlinked and has no parent, then it is |
| 933 | // completely empty. |
| 934 | auto parent = lockedDir.getParent(); |
| 935 | if (!parent) { |
| 936 | return 0; |
| 937 | } |
| 938 | |
| 939 | off_t bytesRead = 0; |
| 940 | const auto& dirents = openFile->dirents; |
| 941 | for (; index < dirents.size() && bytesRead + sizeof(dirent) <= count; |
| 942 | index++) { |
| 943 | const auto& entry = dirents[index]; |
| 944 | result->d_ino = entry.ino; |
| 945 | result->d_off = index + 1; |
| 946 | result->d_reclen = sizeof(dirent); |
| 947 | switch (entry.kind) { |
| 948 | case File::UnknownKind: |
| 949 | result->d_type = DT_UNKNOWN; |
| 950 | break; |
| 951 | case File::DataFileKind: |
| 952 | result->d_type = DT_REG; |
| 953 | break; |
| 954 | case File::DirectoryKind: |
| 955 | result->d_type = DT_DIR; |
| 956 | break; |
| 957 | case File::SymlinkKind: |
| 958 | result->d_type = DT_LNK; |
| 959 | break; |
| 960 | default: |
| 961 | result->d_type = DT_UNKNOWN; |
| 962 | break; |
| 963 | } |
| 964 | assert(entry.name.size() + 1 <= sizeof(result->d_name)); |
| 965 | strcpy(result->d_name, entry.name.c_str()); |
| 966 | ++result; |
nothing calls this directly
no test coverage detected