[klibc] [PATCH] dirent.h add fdopendir()
maximilian attems
max at stro.at
Wed Aug 10 11:43:55 PDT 2011
Initial implemenation with quick test.
Signed-off-by: maximilian attems <max at stro.at>
---
Should maybe go to a seperate file too..
usr/include/dirent.h | 1 +
usr/klibc/readdir.c | 37 ++++++++++++++++++++++++++++++++++++-
usr/klibc/tests/Kbuild | 1 +
usr/klibc/tests/fdopendir.c | 31 +++++++++++++++++++++++++++++++
4 files changed, 69 insertions(+), 1 deletions(-)
create mode 100644 usr/klibc/tests/fdopendir.c
diff --git a/usr/include/dirent.h b/usr/include/dirent.h
index 725452e..bc08c5c 100644
--- a/usr/include/dirent.h
+++ b/usr/include/dirent.h
@@ -23,6 +23,7 @@ struct _IO_dir {
typedef struct _IO_dir DIR;
__extern DIR *opendir(const char *);
+__extern DIR *fdopendir(int);
__extern struct dirent *readdir(DIR *);
__extern int closedir(DIR *);
static __inline__ int dirfd(DIR * __d)
diff --git a/usr/klibc/readdir.c b/usr/klibc/readdir.c
index 453fc08..1ea8b99 100644
--- a/usr/klibc/readdir.c
+++ b/usr/klibc/readdir.c
@@ -1,10 +1,13 @@
/*
- * readdir.c: opendir/readdir/closedir
+ * readdir.c: opendir/fdopendir/readdir/closedir
*/
+#include <sys/types.h>
+#include <sys/stat.h>
#include <unistd.h>
#include <fcntl.h>
#include <stdlib.h>
+#include <errno.h>
#define __KLIBC_DIRENT_INTERNALS
#include <dirent.h>
@@ -28,6 +31,38 @@ DIR *opendir(const char *name)
return dp;
}
+DIR *fdopendir(int fd)
+{
+ DIR *dp;
+ int flags;
+ struct stat st;
+
+ if (fstat(fd, &st))
+ return NULL;
+ if (!S_ISDIR(st.st_mode)) {
+ errno = ENOTDIR;
+ return NULL;
+ }
+
+ flags = fcntl(fd, F_GETFL);
+ if (flags == -1)
+ return NULL;
+ if ((flags & O_ACCMODE) == O_WRONLY) {
+ errno = EINVAL;
+ return NULL;
+ }
+
+ dp = malloc(sizeof(DIR));
+
+ if(!dp)
+ return NULL;
+
+ dp->__fd = fd;
+ dp->next = NULL;
+ dp->bytes_left = 0;
+ return dp;
+}
+
struct dirent *readdir(DIR *dir)
{
struct dirent *dent;
diff --git a/usr/klibc/tests/Kbuild b/usr/klibc/tests/Kbuild
index a3e0254..5e6e073 100644
--- a/usr/klibc/tests/Kbuild
+++ b/usr/klibc/tests/Kbuild
@@ -14,6 +14,7 @@ static-y := $(test-files:.c=)
shared-y := $(addsuffix .shared, $(static-y))
environ.shared-y := environ.o
+fdopendir.shared-y := fdopendir.o
fcntl.shared-y := fcntl.o
fnmatch.shared-y := fnmatch.o
getopttest.shared-y := getopttest.o
diff --git a/usr/klibc/tests/fdopendir.c b/usr/klibc/tests/fdopendir.c
new file mode 100644
index 0000000..14bd99b
--- /dev/null
+++ b/usr/klibc/tests/fdopendir.c
@@ -0,0 +1,31 @@
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <dirent.h>
+#include <stdio.h>
+
+int main()
+{
+ DIR *dir;
+ struct dirent dirent;
+ int fd;
+
+ /* XXX: use mktemps */
+ fd = open("/tmp/", O_RDONLY);
+ if (fd < 0) {
+ perror("open");
+ return 1;
+ }
+
+ dir = fdopendir(fd);
+ if (!dir) {
+ perror("fdopendir");
+ close(fd):
+ return 1;
+ }
+ while ((dirent = readdir(dir)) != NULL)
+ ;
+
+ closedir(dir):
+ return 0;
+}
--
1.7.5.4
More information about the klibc
mailing list