* Added fdopendir() (POSIX).
* Got rid of <dirent_private.h> -- the __DIR structure is private to dirent.c, now. The attribute directory, index directory, and query functions use the the public POSIX API, so does the kernel module code. Those components were not initializing the structure correctly anymore since the introduction of telldir()/seekdir(). +alphabranch git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@32819 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
parent
781aa0f579
commit
adbf8b25f8
@ -32,16 +32,16 @@ typedef struct __DIR DIR;
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
DIR *opendir(const char *dirname);
|
||||
struct dirent *readdir(DIR *dir);
|
||||
int readdir_r(DIR *dir, struct dirent *entry, struct dirent **_result);
|
||||
int closedir(DIR *dir);
|
||||
void rewinddir(DIR *dir);
|
||||
void seekdir(DIR *dir, long int loc);
|
||||
long int telldir(DIR *);
|
||||
|
||||
/* Non-POSIX extension to get the FD out of the private DIR */
|
||||
int dirfd(const DIR *dir);
|
||||
DIR* fdopendir(int fd);
|
||||
DIR* opendir(const char* dirName);
|
||||
struct dirent* readdir(DIR* dir);
|
||||
int readdir_r(DIR* dir, struct dirent* entry,
|
||||
struct dirent** _result);
|
||||
int closedir(DIR* dir);
|
||||
void rewinddir(DIR* dir);
|
||||
void seekdir(DIR* dir, long int position);
|
||||
long int telldir(DIR* dir);
|
||||
int dirfd(const DIR* dir);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
@ -1,24 +0,0 @@
|
||||
/*
|
||||
* Copyright 2008, Axel Dörfler, axeld@pinc-software.de.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*/
|
||||
#ifndef DIRENT_PRIVATE_H
|
||||
#define DIRENT_PRIVATE_H
|
||||
|
||||
|
||||
#include <dirent.h>
|
||||
|
||||
|
||||
#define DIR_BUFFER_SIZE 4096
|
||||
#define DIRENT_BUFFER_SIZE (DIR_BUFFER_SIZE - offsetof(struct __DIR, first_entry))
|
||||
|
||||
struct __DIR {
|
||||
int fd;
|
||||
short next_entry;
|
||||
unsigned short entries_left;
|
||||
long seek_position;
|
||||
long current_position;
|
||||
struct dirent first_entry;
|
||||
};
|
||||
|
||||
#endif /* DIRENT_PRIVATE_H */
|
@ -11,6 +11,7 @@
|
||||
|
||||
#include <kmodule.h>
|
||||
|
||||
#include <dirent.h>
|
||||
#include <errno.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
@ -19,8 +20,6 @@
|
||||
#include <FindDirectory.h>
|
||||
#include <NodeMonitor.h>
|
||||
|
||||
#include <dirent_private.h>
|
||||
|
||||
#include <boot_device.h>
|
||||
#include <boot/elf.h>
|
||||
#include <elf.h>
|
||||
@ -1529,32 +1528,29 @@ ModuleNotificationService::_ScanDirectory(Stack<DIR*>& stack, DIR* dir,
|
||||
}
|
||||
|
||||
struct stat stat;
|
||||
status_t status = vfs_read_stat(dir->fd, dirent->d_name, true, &stat,
|
||||
status_t status = vfs_read_stat(dirfd(dir), dirent->d_name, true, &stat,
|
||||
true);
|
||||
if (status != B_OK)
|
||||
continue;
|
||||
|
||||
if (S_ISDIR(stat.st_mode)) {
|
||||
int fd = _kern_open_dir(dir->fd, dirent->d_name);
|
||||
int fd = _kern_open_dir(dirfd(dir), dirent->d_name);
|
||||
if (fd < 0)
|
||||
continue;
|
||||
|
||||
DIR* subDir = (DIR*)malloc(DIR_BUFFER_SIZE);
|
||||
DIR* subDir = fdopendir(fd);
|
||||
if (subDir == NULL) {
|
||||
close(fd);
|
||||
continue;
|
||||
}
|
||||
|
||||
subDir->fd = fd;
|
||||
subDir->entries_left = 0;
|
||||
|
||||
stack.Push(subDir);
|
||||
|
||||
if (_AddDirectoryNode(stat.st_dev, stat.st_ino) == B_OK
|
||||
&& directMatch)
|
||||
directMatchAdded = true;
|
||||
} else if (S_ISREG(stat.st_mode)) {
|
||||
if (_AddModuleNode(stat.st_dev, stat.st_ino, dir->fd,
|
||||
if (_AddModuleNode(stat.st_dev, stat.st_ino, dirfd(dir),
|
||||
dirent->d_name) == B_OK && directMatch)
|
||||
directMatchAdded = true;
|
||||
}
|
||||
@ -1564,7 +1560,7 @@ ModuleNotificationService::_ScanDirectory(Stack<DIR*>& stack, DIR* dir,
|
||||
// We need to monitor this directory to see if a matching file
|
||||
// is added.
|
||||
struct stat stat;
|
||||
status_t status = vfs_read_stat(dir->fd, NULL, true, &stat, true);
|
||||
status_t status = vfs_read_stat(dirfd(dir), NULL, true, &stat, true);
|
||||
if (status == B_OK)
|
||||
_AddDirectoryNode(stat.st_dev, stat.st_ino);
|
||||
}
|
||||
|
@ -3,7 +3,7 @@ SubDir HAIKU_TOP src system libroot os ;
|
||||
UsePrivateSystemHeaders ;
|
||||
UsePrivateHeaders kernel ;
|
||||
# for util/KMessage.h
|
||||
UsePrivateHeaders libroot runtime_loader ;
|
||||
UsePrivateHeaders libroot runtime_loader shared ;
|
||||
|
||||
MergeObject os_main.o :
|
||||
area.c
|
||||
|
@ -6,26 +6,18 @@
|
||||
|
||||
#include <fs_attr.h>
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <fcntl.h>
|
||||
#include <syscall_utils.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "dirent_private.h"
|
||||
#include "syscalls.h"
|
||||
#include <syscalls.h>
|
||||
#include <syscall_utils.h>
|
||||
|
||||
|
||||
// TODO: think about adding special syscalls for the read/write/stat functions
|
||||
// to speed them up
|
||||
|
||||
#define RETURN_AND_SET_ERRNO(status) \
|
||||
{ \
|
||||
if (status < 0) { \
|
||||
errno = status; \
|
||||
return -1; \
|
||||
} \
|
||||
return status; \
|
||||
}
|
||||
|
||||
|
||||
static DIR *
|
||||
open_attr_dir(int file, const char *path)
|
||||
@ -38,16 +30,12 @@ open_attr_dir(int file, const char *path)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* allocate the memory for the DIR structure */
|
||||
if ((dir = (DIR *)malloc(DIR_BUFFER_SIZE)) == NULL) {
|
||||
errno = B_NO_MEMORY;
|
||||
// allocate the DIR structure
|
||||
if ((dir = fdopendir(fd)) == NULL) {
|
||||
_kern_close(fd);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
dir->fd = fd;
|
||||
dir->entries_left = 0;
|
||||
|
||||
return dir;
|
||||
}
|
||||
|
||||
@ -151,11 +139,7 @@ fs_fopen_attr_dir(int fd)
|
||||
extern "C" int
|
||||
fs_close_attr_dir(DIR* dir)
|
||||
{
|
||||
int status = _kern_close(dir->fd);
|
||||
|
||||
free(dir);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
return closedir(dir);
|
||||
}
|
||||
|
||||
|
||||
|
@ -6,22 +6,13 @@
|
||||
|
||||
#include <fs_index.h>
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <fcntl.h>
|
||||
#include <dirent.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <dirent_private.h>
|
||||
#include <syscalls.h>
|
||||
|
||||
|
||||
#define RETURN_AND_SET_ERRNO(status) \
|
||||
{ \
|
||||
if (status < 0) { \
|
||||
errno = status; \
|
||||
return -1; \
|
||||
} \
|
||||
return status; \
|
||||
}
|
||||
#include <syscall_utils.h>
|
||||
|
||||
|
||||
int
|
||||
@ -72,16 +63,12 @@ fs_open_index_dir(dev_t device)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* allocate the memory for the DIR structure */
|
||||
if ((dir = (DIR *)malloc(DIR_BUFFER_SIZE)) == NULL) {
|
||||
errno = B_NO_MEMORY;
|
||||
// allocate the DIR structure
|
||||
if ((dir = fdopendir(fd)) == NULL) {
|
||||
_kern_close(fd);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
dir->fd = fd;
|
||||
dir->entries_left = 0;
|
||||
|
||||
return dir;
|
||||
}
|
||||
|
||||
@ -89,11 +76,7 @@ fs_open_index_dir(dev_t device)
|
||||
int
|
||||
fs_close_index_dir(DIR *dir)
|
||||
{
|
||||
int status = _kern_close(dir->fd);
|
||||
|
||||
free(dir);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
return closedir(dir);
|
||||
}
|
||||
|
||||
|
||||
|
@ -6,13 +6,14 @@
|
||||
|
||||
#include <fs_query.h>
|
||||
|
||||
#include <dirent.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <fcntl.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include <dirent_private.h>
|
||||
#include <syscalls.h>
|
||||
#include <syscall_utils.h>
|
||||
|
||||
|
||||
static DIR *
|
||||
@ -31,17 +32,13 @@ open_query_etc(dev_t device, const char *query,
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// allocate a DIR
|
||||
DIR *dir = (DIR *)malloc(DIR_BUFFER_SIZE);
|
||||
if (!dir) {
|
||||
// allocate the DIR structure
|
||||
DIR *dir = fdopendir(fd);
|
||||
if (dir == NULL) {
|
||||
_kern_close(fd);
|
||||
errno = B_NO_MEMORY;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
dir->fd = fd;
|
||||
dir->entries_left = 0;
|
||||
|
||||
return dir;
|
||||
}
|
||||
|
||||
@ -70,14 +67,7 @@ fs_open_live_query(dev_t device, const char *query,
|
||||
int
|
||||
fs_close_query(DIR *dir)
|
||||
{
|
||||
if (dir == NULL) {
|
||||
errno = B_BAD_VALUE;
|
||||
return -1;
|
||||
}
|
||||
|
||||
int fd = dir->fd;
|
||||
free(dir);
|
||||
return _kern_close(fd);
|
||||
return closedir(dir);
|
||||
}
|
||||
|
||||
|
||||
|
@ -6,15 +6,28 @@
|
||||
|
||||
|
||||
#include <dirent.h>
|
||||
|
||||
#include <errno.h>
|
||||
#include <limits.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include <dirent_private.h>
|
||||
#include <syscalls.h>
|
||||
#include <syscall_utils.h>
|
||||
|
||||
|
||||
#define DIR_BUFFER_SIZE 4096
|
||||
|
||||
|
||||
struct __DIR {
|
||||
int fd;
|
||||
short next_entry;
|
||||
unsigned short entries_left;
|
||||
long seek_position;
|
||||
long current_position;
|
||||
struct dirent first_entry;
|
||||
};
|
||||
|
||||
|
||||
static int
|
||||
do_seek_dir(DIR* dir)
|
||||
{
|
||||
@ -62,8 +75,8 @@ do_seek_dir(DIR* dir)
|
||||
dir->current_position += dir->entries_left;
|
||||
dir->entries_left = 0;
|
||||
|
||||
count = _kern_read_dir(dir->fd, &dir->first_entry, DIRENT_BUFFER_SIZE,
|
||||
USHRT_MAX);
|
||||
count = _kern_read_dir(dir->fd, &dir->first_entry,
|
||||
(char*)dir + DIR_BUFFER_SIZE - (char*)&dir->first_entry, USHRT_MAX);
|
||||
if (count <= 0) {
|
||||
if (count < 0)
|
||||
errno = count;
|
||||
@ -83,21 +96,14 @@ do_seek_dir(DIR* dir)
|
||||
// #pragma mark -
|
||||
|
||||
|
||||
DIR *
|
||||
opendir(const char *path)
|
||||
DIR*
|
||||
fdopendir(int fd)
|
||||
{
|
||||
DIR *dir;
|
||||
|
||||
int fd = _kern_open_dir(-1, path);
|
||||
if (fd < 0) {
|
||||
errno = fd;
|
||||
return NULL;
|
||||
}
|
||||
DIR* dir;
|
||||
|
||||
/* allocate the memory for the DIR structure */
|
||||
if ((dir = (DIR *)malloc(DIR_BUFFER_SIZE)) == NULL) {
|
||||
if ((dir = (DIR*)malloc(DIR_BUFFER_SIZE)) == NULL) {
|
||||
errno = B_NO_MEMORY;
|
||||
_kern_close(fd);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
@ -110,10 +116,38 @@ opendir(const char *path)
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
closedir(DIR *dir)
|
||||
DIR*
|
||||
opendir(const char* path)
|
||||
{
|
||||
int status = _kern_close(dir->fd);
|
||||
DIR* dir;
|
||||
|
||||
int fd = _kern_open_dir(-1, path);
|
||||
if (fd < 0) {
|
||||
errno = fd;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// allocate the DIR structure
|
||||
if ((dir = fdopendir(fd)) == NULL) {
|
||||
_kern_close(fd);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return dir;
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
closedir(DIR* dir)
|
||||
{
|
||||
int status;
|
||||
|
||||
if (dir == NULL) {
|
||||
errno = B_BAD_VALUE;
|
||||
return -1;
|
||||
}
|
||||
|
||||
status = _kern_close(dir->fd);
|
||||
|
||||
free(dir);
|
||||
|
||||
@ -121,8 +155,8 @@ closedir(DIR *dir)
|
||||
}
|
||||
|
||||
|
||||
struct dirent *
|
||||
readdir(DIR *dir)
|
||||
struct dirent*
|
||||
readdir(DIR* dir)
|
||||
{
|
||||
ssize_t count;
|
||||
|
||||
@ -145,8 +179,8 @@ readdir(DIR *dir)
|
||||
|
||||
// we need to retrieve new entries
|
||||
|
||||
count = _kern_read_dir(dir->fd, &dir->first_entry, DIRENT_BUFFER_SIZE,
|
||||
USHRT_MAX);
|
||||
count = _kern_read_dir(dir->fd, &dir->first_entry,
|
||||
(char*)dir + DIR_BUFFER_SIZE - (char*)&dir->first_entry, USHRT_MAX);
|
||||
if (count <= 0) {
|
||||
if (count < 0)
|
||||
errno = count;
|
||||
@ -165,7 +199,7 @@ readdir(DIR *dir)
|
||||
|
||||
|
||||
int
|
||||
readdir_r(DIR *dir, struct dirent *entry, struct dirent **_result)
|
||||
readdir_r(DIR* dir, struct dirent* entry, struct dirent** _result)
|
||||
{
|
||||
ssize_t count = _kern_read_dir(dir->fd, entry, sizeof(struct dirent)
|
||||
+ B_FILE_NAME_LENGTH, 1);
|
||||
@ -183,7 +217,7 @@ readdir_r(DIR *dir, struct dirent *entry, struct dirent **_result)
|
||||
|
||||
|
||||
void
|
||||
rewinddir(DIR *dir)
|
||||
rewinddir(DIR* dir)
|
||||
{
|
||||
dir->seek_position = 0;
|
||||
}
|
||||
@ -204,7 +238,7 @@ telldir(DIR* dir)
|
||||
|
||||
|
||||
int
|
||||
dirfd(const DIR *dir)
|
||||
dirfd(const DIR* dir)
|
||||
{
|
||||
return dir->fd;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user