[haiku-commits] haiku: hrev50292 - in src: tests/system/libroot/posix system/libroot/posix

  • From: jerome.duval@xxxxxxxxx
  • To: haiku-commits@xxxxxxxxxxxxx
  • Date: Sat, 7 May 2016 16:43:28 +0200 (CEST)

hrev50292 adds 1 changeset to branch 'master'
old head: 60f1f7efe4cf56aa3c2ce4542dbdc07cebfa326f
new head: f022c304b0bb15a43ed08a34e0bf18a751db8341
overview: 
http://cgit.haiku-os.org/haiku/log/?qt=range&q=f022c304b0bb+%5E60f1f7efe4cf

----------------------------------------------------------------------------

f022c304b0bb: readdir_r(): uses the logic of readdir()...
  
  to retrieve more than one entry.
  * readdir_r() is now affected by rewinddir(), thus fixing #12755.
  * extends dirent_test with readdir_r().

                                   [ Jérôme Duval <jerome.duval@xxxxxxxxx> ]

----------------------------------------------------------------------------

Revision:    hrev50292
Commit:      f022c304b0bb15a43ed08a34e0bf18a751db8341
URL:         http://cgit.haiku-os.org/haiku/commit/?id=f022c304b0bb
Author:      Jérôme Duval <jerome.duval@xxxxxxxxx>
Date:        Sat May  7 14:35:14 2016 UTC

Ticket:      https://dev.haiku-os.org/ticket/12755

----------------------------------------------------------------------------

2 files changed, 72 insertions(+), 3 deletions(-)
src/system/libroot/posix/dirent.c              | 28 ++++++++++++-
src/tests/system/libroot/posix/dirent_test.cpp | 47 +++++++++++++++++++++-

----------------------------------------------------------------------------

diff --git a/src/system/libroot/posix/dirent.c 
b/src/system/libroot/posix/dirent.c
index 09f5f5f..198c23d 100644
--- a/src/system/libroot/posix/dirent.c
+++ b/src/system/libroot/posix/dirent.c
@@ -243,7 +243,26 @@ readdir(DIR* dir)
 int
 readdir_r(DIR* dir, struct dirent* entry, struct dirent** _result)
 {
-       ssize_t count = _kern_read_dir(dir->fd, entry, sizeof(struct dirent)
+       ssize_t count;
+
+       if (dir->seek_position != dir->current_position) {
+               if (do_seek_dir(dir) != 0)
+                       return -1;
+       }
+
+       if (dir->entries_left > 0) {
+               *_result
+                       = (struct dirent *)((uint8 *)&dir->first_entry + 
dir->next_entry);
+
+               dir->entries_left--;
+               dir->next_entry += (*_result)->d_reclen;
+               dir->seek_position++;
+               dir->current_position++;
+
+               return 0;
+       }
+
+       count = _kern_read_dir(dir->fd, entry, sizeof(struct dirent)
                + B_FILE_NAME_LENGTH, 1);
        if (count < B_OK)
                return count;
@@ -251,8 +270,13 @@ readdir_r(DIR* dir, struct dirent* entry, struct dirent** 
_result)
        if (count == 0) {
                // end of directory
                *_result = NULL;
-       } else
+       } else {
                *_result = entry;
+               dir->entries_left = count - 1;
+               dir->next_entry = dir->first_entry.d_reclen;
+               dir->seek_position++;
+               dir->current_position++;
+       }
 
        return 0;
 }
diff --git a/src/tests/system/libroot/posix/dirent_test.cpp 
b/src/tests/system/libroot/posix/dirent_test.cpp
index 833417e..da5a470 100644
--- a/src/tests/system/libroot/posix/dirent_test.cpp
+++ b/src/tests/system/libroot/posix/dirent_test.cpp
@@ -6,15 +6,18 @@
 
 #include <dirent.h>
 #include <stdio.h>
+#include <stdlib.h>
 
 
 int
 main(int argc, char** argv)
 {
+       dirent *buf, *dirent;
        DIR* dir = opendir(".");
 
+       printf("first pass:\n");
        while (true) {
-               dirent* dirent = readdir(dir);
+               dirent = readdir(dir);
                if (dirent == NULL)
                        break;
 
@@ -23,6 +26,48 @@ main(int argc, char** argv)
                //printf("  left: %u, next: %d\n", dir->entries_left, 
dir->next_entry);
        }
 
+       rewinddir(dir);
+       printf("second pass:\n");
+       while (true) {
+               dirent = readdir(dir);
+               if (dirent == NULL)
+                       break;
+
+               printf("Entry: dev %ld, ino %Ld, name \"%s\"\n", dirent->d_dev,
+                       dirent->d_ino, dirent->d_name);
+               //printf("  left: %u, next: %d\n", dir->entries_left, 
dir->next_entry);
+       }
+
+
        closedir(dir);
+
+       dirent = NULL;
+       buf = (struct dirent*)malloc(sizeof(struct dirent) + NAME_MAX);
+
+       dir = opendir(".");
+
+       printf("first pass:\n");
+       while (true) {
+               if (readdir_r(dir, buf, &dirent) != 0 || dirent == NULL)
+                       break;
+
+               printf("Entry: dev %ld, ino %Ld, name \"%s\"\n", dirent->d_dev,
+                       dirent->d_ino, dirent->d_name);
+               //printf("  left: %u, next: %d\n", dir->entries_left, 
dir->next_entry);
+       }
+
+       rewinddir(dir);
+       printf("second pass:\n");
+       while (true) {
+               if (readdir_r(dir, buf, &dirent) != 0 || dirent == NULL)
+                       break;
+
+               printf("Entry: dev %ld, ino %Ld, name \"%s\"\n", dirent->d_dev,
+                       dirent->d_ino, dirent->d_name);
+               //printf("  left: %u, next: %d\n", dir->entries_left, 
dir->next_entry);
+       }
+
+       closedir(dir);
+
        return 0;
 }


Other related posts: