diff --git a/kernel/src/sys/stdio.cpp b/kernel/src/sys/stdio.cpp index 790d49dc..40727a0a 100644 --- a/kernel/src/sys/stdio.cpp +++ b/kernel/src/sys/stdio.cpp @@ -16,6 +16,7 @@ #define OPEN_WRITE 2 #define OPEN_NONBLOCK 4 #define OPEN_CLOEXEC 8 +#define OPEN_DIRECTORY 16 #define SEEK_SET 0 #define SEEK_CUR 1 @@ -184,6 +185,15 @@ void sys_open(Context* context, const char* filename, int flags) bool able_to_block = (flags & OPEN_NONBLOCK) == 0; bool close_on_exec = (flags & OPEN_CLOEXEC) > 0; + bool only_directory = (flags & OPEN_DIRECTORY) > 0; + + if (only_directory && node->type != VFS_DIRECTORY) + { + kfree(kfilename); + context->rax = -ENOTDIR; + return; + } + kdbgln("open(): opening %s %s, allocated file descriptor %d", kfilename, (can_read && can_write) ? "rw" : can_read ? "r-" diff --git a/libs/libc/include/fcntl.h b/libs/libc/include/fcntl.h index b17e3689..fa306abe 100644 --- a/libs/libc/include/fcntl.h +++ b/libs/libc/include/fcntl.h @@ -11,6 +11,8 @@ #define O_NONBLOCK 4 /* Close the opened file descriptor on a call to execve(). */ #define O_CLOEXEC 8 +/* Refuse to open the file if it is not a directory. */ +#define O_DIRECTORY 16 /* Duplicate a file descriptor. */ #define F_DUPFD 0 diff --git a/libs/libc/src/dirent.cpp b/libs/libc/src/dirent.cpp index 5924abf0..5447647c 100644 --- a/libs/libc/src/dirent.cpp +++ b/libs/libc/src/dirent.cpp @@ -10,7 +10,7 @@ extern "C" { DIR* opendir(const char* path) { - int dirfd = open(path, O_RDONLY); // FIXME: Implement O_DIRECTORY and use that. + int dirfd = open(path, O_RDONLY | O_DIRECTORY); if (dirfd < 0) return NULL; return fdopendir(dirfd); }