* Renamed fs_attr.c to fs_attr.cpp and cleaned it up a bit.
* Always use _kern_create_attr() in fs_write_attr(), or otherwise it might not
be created when it should.
* Stippi special: fixed typo "in another words" -> "in other words" ("a" is
singular, not plural).
git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@31312 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -11,7 +11,7 @@ MergeObject os_main.o :
|
||||
debug.c
|
||||
driver_settings.c
|
||||
find_directory.c
|
||||
fs_attr.c
|
||||
fs_attr.cpp
|
||||
fs_index.c
|
||||
fs_info.c
|
||||
fs_query.cpp
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2002-2008, Axel Dörfler, axeld@pinc-software.de.
|
||||
* Copyright 2002-2009, Axel Dörfler, axeld@pinc-software.de.
|
||||
* Distributed under the terms of the MIT License.
|
||||
*/
|
||||
|
||||
@@ -27,131 +27,6 @@
|
||||
}
|
||||
|
||||
|
||||
ssize_t
|
||||
fs_read_attr(int fd, const char *attribute, uint32 type,
|
||||
off_t pos, void *buffer, size_t readBytes)
|
||||
{
|
||||
ssize_t bytes;
|
||||
|
||||
int attr = _kern_open_attr(fd, attribute, O_RDONLY);
|
||||
if (attr < 0)
|
||||
RETURN_AND_SET_ERRNO(attr);
|
||||
|
||||
// type is not used at all in this function
|
||||
(void)type;
|
||||
|
||||
bytes = _kern_read(attr, pos, buffer, readBytes);
|
||||
_kern_close(attr);
|
||||
|
||||
RETURN_AND_SET_ERRNO(bytes);
|
||||
}
|
||||
|
||||
|
||||
ssize_t
|
||||
fs_write_attr(int fd, const char *attribute, uint32 type,
|
||||
off_t pos, const void *buffer, size_t writeBytes)
|
||||
{
|
||||
// NOTE: This call is deprecated in Haiku and has a number of problems:
|
||||
// On BeOS, it was documented that the "pos" argument is ignored.
|
||||
// However, a number of programs tried to use this call to write large
|
||||
// attributes in a loop anyways. These programs all relied on the broken
|
||||
// or at least inconsistent behaviour to truncate/clobber an existing
|
||||
// attribute. In another words, writing 5 bytes at position 0 into an
|
||||
// attribute that was already 10 bytes long resulted in an attribute of
|
||||
// only 5 bytes length.
|
||||
// The implementation of this function tries to stay compatible with
|
||||
// BeOS in that it clobbers the existing attribute when you write at offset
|
||||
// 0, but it also tries to support programs which continue to write more
|
||||
// chunks.
|
||||
// The new Haiku way is to use fs_open_attr() to get a regular file handle
|
||||
// and use that for writing, then use fs_close_attr() when done. As you
|
||||
// see from this implementation, it saves 2 syscalls per writing a chunk
|
||||
// of data.
|
||||
|
||||
ssize_t bytes;
|
||||
int attr = -1;
|
||||
|
||||
// If pos is 0, we try to avoid one syscall that with good chances
|
||||
// will fail anyways and take the shortcut to creating the attr directly.
|
||||
if (pos > 0)
|
||||
attr = _kern_open_attr(fd, attribute, O_WRONLY);
|
||||
if (attr < 0) {
|
||||
attr = _kern_create_attr(fd, attribute, type, O_WRONLY | O_TRUNC);
|
||||
if (attr < 0)
|
||||
RETURN_AND_SET_ERRNO(attr);
|
||||
}
|
||||
|
||||
bytes = _kern_write(attr, pos, buffer, writeBytes);
|
||||
_kern_close(attr);
|
||||
|
||||
RETURN_AND_SET_ERRNO(bytes);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
fs_remove_attr(int fd, const char *attribute)
|
||||
{
|
||||
status_t status = _kern_remove_attr(fd, attribute);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
fs_stat_attr(int fd, const char *attribute, struct attr_info *attrInfo)
|
||||
{
|
||||
struct stat stat;
|
||||
status_t status;
|
||||
|
||||
int attr = _kern_open_attr(fd, attribute, O_RDONLY);
|
||||
if (attr < 0)
|
||||
RETURN_AND_SET_ERRNO(attr);
|
||||
|
||||
status = _kern_read_stat(attr, NULL, false, &stat, sizeof(struct stat));
|
||||
if (status == B_OK) {
|
||||
attrInfo->type = stat.st_type;
|
||||
attrInfo->size = stat.st_size;
|
||||
}
|
||||
_kern_close(attr);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
int
|
||||
fs_open_attr(const char *path, const char *attribute, uint32 type, int openMode)
|
||||
{
|
||||
// TODO: implement fs_open_attr() - or remove it completely
|
||||
// if it will be implemented, rename the current fs_open_attr() to fs_fopen_attr()
|
||||
return B_ERROR;
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
int
|
||||
fs_open_attr(int fd, const char *attribute, uint32 type, int openMode)
|
||||
{
|
||||
status_t status;
|
||||
|
||||
if (openMode & O_CREAT)
|
||||
status = _kern_create_attr(fd, attribute, type, openMode);
|
||||
else
|
||||
status = _kern_open_attr(fd, attribute, openMode);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
fs_close_attr(int fd)
|
||||
{
|
||||
status_t status = _kern_close(fd);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
}
|
||||
|
||||
|
||||
static DIR *
|
||||
open_attr_dir(int file, const char *path)
|
||||
{
|
||||
@@ -177,22 +52,136 @@ open_attr_dir(int file, const char *path)
|
||||
}
|
||||
|
||||
|
||||
DIR *
|
||||
fs_open_attr_dir(const char *path)
|
||||
// #pragma mark -
|
||||
|
||||
|
||||
extern "C" ssize_t
|
||||
fs_read_attr(int fd, const char* attribute, uint32 /*type*/, off_t pos,
|
||||
void* buffer, size_t readBytes)
|
||||
{
|
||||
int attr = _kern_open_attr(fd, attribute, O_RDONLY);
|
||||
if (attr < 0)
|
||||
RETURN_AND_SET_ERRNO(attr);
|
||||
|
||||
ssize_t bytes = _kern_read(attr, pos, buffer, readBytes);
|
||||
_kern_close(attr);
|
||||
|
||||
RETURN_AND_SET_ERRNO(bytes);
|
||||
}
|
||||
|
||||
|
||||
extern "C" ssize_t
|
||||
fs_write_attr(int fd, const char* attribute, uint32 type, off_t pos,
|
||||
const void* buffer, size_t writeBytes)
|
||||
{
|
||||
// NOTE: This call is deprecated in Haiku and has a number of problems:
|
||||
// On BeOS, it was documented that the "pos" argument is ignored.
|
||||
// However, a number of programs tried to use this call to write large
|
||||
// attributes in a loop anyways. These programs all relied on the broken
|
||||
// or at least inconsistent behaviour to truncate/clobber an existing
|
||||
// attribute. In other words, writing 5 bytes at position 0 into an
|
||||
// attribute that was already 10 bytes long resulted in an attribute of
|
||||
// only 5 bytes length.
|
||||
// The implementation of this function tries to stay compatible with
|
||||
// BeOS in that it clobbers the existing attribute when you write at offset
|
||||
// 0, but it also tries to support programs which continue to write more
|
||||
// chunks.
|
||||
// The new Haiku way is to use fs_open_attr() to get a regular file handle
|
||||
// and use that for writing, then use fs_close_attr() when done. As you
|
||||
// see from this implementation, it saves 2 syscalls per writing a chunk
|
||||
// of data.
|
||||
|
||||
int attr = _kern_create_attr(fd, attribute, type,
|
||||
O_WRONLY | (pos != 0 ? 0 : O_TRUNC));
|
||||
if (attr < 0)
|
||||
RETURN_AND_SET_ERRNO(attr);
|
||||
|
||||
ssize_t bytes = _kern_write(attr, pos, buffer, writeBytes);
|
||||
_kern_close(attr);
|
||||
|
||||
RETURN_AND_SET_ERRNO(bytes);
|
||||
}
|
||||
|
||||
|
||||
extern "C" int
|
||||
fs_remove_attr(int fd, const char* attribute)
|
||||
{
|
||||
status_t status = _kern_remove_attr(fd, attribute);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
}
|
||||
|
||||
|
||||
extern "C" int
|
||||
fs_stat_attr(int fd, const char* attribute, struct attr_info* attrInfo)
|
||||
{
|
||||
int attr = _kern_open_attr(fd, attribute, O_RDONLY);
|
||||
if (attr < 0)
|
||||
RETURN_AND_SET_ERRNO(attr);
|
||||
|
||||
struct stat stat;
|
||||
status_t status = _kern_read_stat(attr, NULL, false, &stat,
|
||||
sizeof(struct stat));
|
||||
if (status == B_OK) {
|
||||
attrInfo->type = stat.st_type;
|
||||
attrInfo->size = stat.st_size;
|
||||
}
|
||||
_kern_close(attr);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
int
|
||||
fs_open_attr(const char *path, const char *attribute, uint32 type, int openMode)
|
||||
{
|
||||
// TODO: implement fs_open_attr() - or remove it completely
|
||||
// if it will be implemented, rename the current fs_open_attr() to fs_fopen_attr()
|
||||
return B_ERROR;
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
extern "C" int
|
||||
fs_open_attr(int fd, const char* attribute, uint32 type, int openMode)
|
||||
{
|
||||
status_t status;
|
||||
|
||||
if ((openMode & O_CREAT) != 0)
|
||||
status = _kern_create_attr(fd, attribute, type, openMode);
|
||||
else
|
||||
status = _kern_open_attr(fd, attribute, openMode);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
}
|
||||
|
||||
|
||||
extern "C" int
|
||||
fs_close_attr(int fd)
|
||||
{
|
||||
status_t status = _kern_close(fd);
|
||||
|
||||
RETURN_AND_SET_ERRNO(status);
|
||||
}
|
||||
|
||||
|
||||
extern "C" DIR*
|
||||
fs_open_attr_dir(const char* path)
|
||||
{
|
||||
return open_attr_dir(-1, path);
|
||||
}
|
||||
|
||||
|
||||
DIR *
|
||||
extern "C" DIR*
|
||||
fs_fopen_attr_dir(int fd)
|
||||
{
|
||||
return open_attr_dir(fd, NULL);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
fs_close_attr_dir(DIR *dir)
|
||||
extern "C" int
|
||||
fs_close_attr_dir(DIR* dir)
|
||||
{
|
||||
int status = _kern_close(dir->fd);
|
||||
|
||||
@@ -202,15 +191,15 @@ fs_close_attr_dir(DIR *dir)
|
||||
}
|
||||
|
||||
|
||||
struct dirent *
|
||||
fs_read_attr_dir(DIR *dir)
|
||||
extern "C" struct dirent*
|
||||
fs_read_attr_dir(DIR* dir)
|
||||
{
|
||||
return readdir(dir);
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
fs_rewind_attr_dir(DIR *dir)
|
||||
extern "C" void
|
||||
fs_rewind_attr_dir(DIR* dir)
|
||||
{
|
||||
rewinddir(dir);
|
||||
}
|
||||
Reference in New Issue
Block a user