diff --git a/src/kernel/core/fd.c b/src/kernel/core/fd.c index 75c1325612..46751c5400 100644 --- a/src/kernel/core/fd.c +++ b/src/kernel/core/fd.c @@ -23,12 +23,31 @@ return EINVAL; -#define PRINT(x) dprintf x +#define TRACE_FD 0 +#if TRACE_FD +# define TRACE(x) dprintf x +# define PRINT(x) dprintf x +#else +# define TRACE(x) +# define PRINT(x) +#endif /*** General fd routines ***/ +#ifdef DEBUG +void dump_fd(int fd, struct file_descriptor *descriptor); + +void +dump_fd(int fd,struct file_descriptor *descriptor) +{ + dprintf("fd[%d] = %p: type = %d, ref_count = %d, ops = %p, vnode = %p, cookie = %p, dummy = %x\n", + fd,descriptor,descriptor->type,descriptor->ref_count,descriptor->ops, + descriptor->vnode,descriptor->cookie,descriptor->dummy); +} +#endif + /** Allocates and initializes a new file_descriptor */ struct file_descriptor * @@ -41,6 +60,7 @@ alloc_fd(void) f->vnode = NULL; f->cookie = NULL; f->ref_count = 1; + f->dummy = 0xdeadbeef; } return f; } @@ -76,15 +96,18 @@ err: void -put_fd(struct file_descriptor *f) +put_fd(struct file_descriptor *descriptor) { /* Run a cleanup (fd_free) routine if there is one and free structure, but only * if we've just removed the final reference to it :) */ - if (atomic_add(&f->ref_count, -1) == 1) { - if (f->ops->fd_free) - f->ops->fd_free(f); - kfree(f); + if (atomic_add(&descriptor->ref_count, -1) == 1) { + if (descriptor->ops->fd_close) + descriptor->ops->fd_close(descriptor); + if (descriptor->ops->fd_free) + descriptor->ops->fd_free(descriptor); + + kfree(descriptor); } } @@ -105,6 +128,7 @@ get_fd(struct io_context *ioctx, int fd) } mutex_unlock(&ioctx->io_mutex); + return f; } @@ -185,23 +209,24 @@ user_write(int fd, const void *buffer, off_t pos, size_t length) } -int -user_seek(int fd, off_t pos, int seek_type) +off_t +user_seek(int fd, off_t pos, int seekType) { struct file_descriptor *descriptor; - int status; descriptor = get_fd(get_current_io_context(false), fd); if (!descriptor) return EBADF; + TRACE(("user_seek(descriptor = %p)\n",descriptor)); + if (descriptor->ops->fd_seek) - status = descriptor->ops->fd_seek(descriptor, pos, seek_type); + pos = descriptor->ops->fd_seek(descriptor, pos, seekType); else - status = EOPNOTSUPP; + pos = ESPIPE; put_fd(descriptor); - return status; + return pos; } @@ -291,6 +316,8 @@ user_fstat(int fd, struct stat *stat) if (descriptor == NULL) return EBADF; + TRACE(("user_fstat(descriptor = %p)\n",descriptor)); + if (descriptor->ops->fd_stat) { // we're using the stat buffer on the stack to not have to // lock the given stat buffer in memory @@ -310,20 +337,18 @@ user_fstat(int fd, struct stat *stat) int user_close(int fd) { - struct io_context *ioContext = get_current_io_context(false); - struct file_descriptor *descriptor = get_fd(ioContext, fd); - int retval; + struct io_context *io = get_current_io_context(false); + struct file_descriptor *descriptor = get_fd(io, fd); if (descriptor == NULL) return EBADF; - if (descriptor->ops->fd_close) - retval = descriptor->ops->fd_close(descriptor, fd, ioContext); - else - retval = EOPNOTSUPP; + TRACE(("user_close(descriptor = %p)\n",descriptor)); + + remove_fd(io, fd); put_fd(descriptor); - return retval; + return B_OK; } @@ -364,7 +389,6 @@ sys_write(int fd, const void *buffer, off_t pos, size_t length) struct file_descriptor *descriptor; ssize_t retval; -// dprintf("sys_write: fd %d\n", fd); // CHECK_SYS_ADDR(buffer) descriptor = get_fd(get_current_io_context(true), fd); @@ -385,23 +409,22 @@ sys_write(int fd, const void *buffer, off_t pos, size_t length) } -int -sys_seek(int fd, off_t pos, int seek_type) +off_t +sys_seek(int fd, off_t pos, int seekType) { struct file_descriptor *descriptor; - int status; descriptor = get_fd(get_current_io_context(true), fd); if (!descriptor) return EBADF; if (descriptor->ops->fd_seek) - status = descriptor->ops->fd_seek(descriptor, pos, seek_type); + pos = descriptor->ops->fd_seek(descriptor, pos, seekType); else - status = EOPNOTSUPP; + pos = ESPIPE; put_fd(descriptor); - return status; + return pos; } @@ -460,7 +483,7 @@ sys_rewind_dir(int fd) struct file_descriptor *descriptor; status_t status; - PRINT(("user_rewind_dir(fd = %d)\n",fd)); + PRINT(("sys_rewind_dir(fd = %d)\n",fd)); descriptor = get_fd(get_current_io_context(true), fd); if (descriptor == NULL) @@ -479,19 +502,15 @@ sys_rewind_dir(int fd) int sys_close(int fd) { - struct io_context *ioContext = get_current_io_context(true); - struct file_descriptor *descriptor = get_fd(ioContext, fd); - int status; + struct io_context *io = get_current_io_context(true); + struct file_descriptor *descriptor = get_fd(io, fd); if (descriptor == NULL) return EBADF; - if (descriptor->ops->fd_close) - status = descriptor->ops->fd_close(descriptor, fd, ioContext); - else - status = EOPNOTSUPP; + remove_fd(io, fd); put_fd(descriptor); - return status; + return B_OK; } diff --git a/src/kernel/core/fs/bootfs.c b/src/kernel/core/fs/bootfs.c index 874f3fc24d..ed277880c2 100755 --- a/src/kernel/core/fs/bootfs.c +++ b/src/kernel/core/fs/bootfs.c @@ -581,7 +581,7 @@ bootfs_removevnode(fs_cookie _fs, fs_vnode _v, bool r) err = 0; err: - if(!r) + if (!r) mutex_unlock(&fs->lock); return err; @@ -714,73 +714,57 @@ bootfs_write(fs_cookie fs, fs_vnode v, file_cookie cookie, const void *buf, off_ } -static int -bootfs_seek(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, off_t pos, int st) +static off_t +bootfs_seek(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, off_t pos, int seekType) { struct bootfs *fs = _fs; struct bootfs_vnode *v = _v; struct bootfs_cookie *cookie = _cookie; - int err = 0; + int err = B_OK; TRACE(("bootfs_seek: vnode 0x%x, cookie 0x%x, pos 0x%x 0x%x, seek_type %d\n", v, cookie, pos, st)); + if (cookie->s->type != STREAM_TYPE_FILE) + return EINVAL; + mutex_lock(&fs->lock); - switch(cookie->s->type) { - case STREAM_TYPE_DIR: - switch(st) { - // only valid args are seek_type SEEK_SET, pos 0. - // this rewinds to beginning of directory - case SEEK_SET: - if(pos == 0) { - cookie->u.dir.ptr = cookie->s->u.dir.dir_head; - } else { - err = ESPIPE; - } - break; - case SEEK_CUR: - case SEEK_END: - default: - err = ESPIPE; - } + switch (seekType) { + case SEEK_SET: + if (pos < 0) + pos = 0; + if (pos > cookie->s->u.file.len) + pos = cookie->s->u.file.len; + cookie->u.file.pos = pos; break; - case STREAM_TYPE_FILE: - switch(st) { - case SEEK_SET: - if(pos < 0) - pos = 0; - if(pos > cookie->s->u.file.len) - pos = cookie->s->u.file.len; - cookie->u.file.pos = pos; - break; - case SEEK_CUR: - if(pos + cookie->u.file.pos > cookie->s->u.file.len) - cookie->u.file.pos = cookie->s->u.file.len; - else if(pos + cookie->u.file.pos < 0) - cookie->u.file.pos = 0; - else - cookie->u.file.pos += pos; - break; - case SEEK_END: - if(pos > 0) - cookie->u.file.pos = cookie->s->u.file.len; - else if(pos + cookie->s->u.file.len < 0) - cookie->u.file.pos = 0; - else - cookie->u.file.pos = pos + cookie->s->u.file.len; - break; - default: - err = EINVAL; - - } + case SEEK_CUR: + if (pos + cookie->u.file.pos > cookie->s->u.file.len) + pos = cookie->s->u.file.len; + else if (pos + cookie->u.file.pos < 0) + pos = 0; + else + pos += cookie->u.file.pos; + break; + case SEEK_END: + if (pos > 0) + pos = cookie->s->u.file.len; + else if (pos + cookie->s->u.file.len < 0) + pos = 0; + else + pos += cookie->s->u.file.len; break; default: err = EINVAL; } + if (err == B_OK) + cookie->u.file.pos = pos; mutex_unlock(&fs->lock); - return err; + if (err < B_OK) + return err; + + return pos; } diff --git a/src/kernel/core/fs/devfs.c b/src/kernel/core/fs/devfs.c index 15344f1742..8ebfccd203 100755 --- a/src/kernel/core/fs/devfs.c +++ b/src/kernel/core/fs/devfs.c @@ -27,9 +27,11 @@ #define DEVFS_TRACE 0 #if DEVFS_TRACE -#define TRACE(x) dprintf x +# define TRACE(x) dprintf x +# define INSANE(x) dprintf x #else -#define TRACE(x) +# define TRACE(x) +# define INSANE(x) #endif struct devfs_part_map { @@ -51,7 +53,7 @@ struct devfs_stream { struct devfs_cookie *jar_head; } dir; struct stream_dev { - void * ident; + void *ident; device_hooks *calls; struct devfs_part_map *part_map; } dev; @@ -77,7 +79,7 @@ struct devfs { }; struct devfs_cookie { - struct devfs_stream *s; + struct devfs_stream *stream; int oflags; union { struct cookie_dir { @@ -92,7 +94,7 @@ struct devfs_cookie { }; /* the one and only allowed devfs instance */ -static struct devfs *thedevfs = NULL; +static struct devfs *gDeviceFileSystem = NULL; #define BOOTFS_HASH_SIZE 16 @@ -103,10 +105,10 @@ devfs_vnode_hash_func(void *_v, const void *_key, unsigned int range) struct devfs_vnode *v = _v; const vnode_id *key = _key; - if(v != NULL) + if (v != NULL) return v->id % range; - else - return (*key) % range; + + return (*key) % range; } @@ -116,10 +118,10 @@ devfs_vnode_compare_func(void *_v, const void *_key) struct devfs_vnode *v = _v; const vnode_id *key = _key; - if(v->id == *key) + if (v->id == *key) return 0; - else - return -1; + + return -1; } @@ -129,14 +131,14 @@ devfs_create_vnode(struct devfs *fs, const char *name) struct devfs_vnode *v; v = kmalloc(sizeof(struct devfs_vnode)); - if(v == NULL) + if (v == NULL) return NULL; memset(v, 0, sizeof(struct devfs_vnode)); v->id = fs->next_vnode_id++; v->name = kstrdup(name); - if(v->name == NULL) { + if (v->name == NULL) { kfree(v); return NULL; } @@ -150,18 +152,19 @@ devfs_delete_vnode(struct devfs *fs, struct devfs_vnode *v, bool force_delete) { // cant delete it if it's in a directory or is a directory // and has children - if(!force_delete && ((v->stream.type == STREAM_TYPE_DIR && v->stream.u.dir.dir_head != NULL) || v->dir_next != NULL)) { + if (!force_delete + && ((v->stream.type == STREAM_TYPE_DIR && v->stream.u.dir.dir_head != NULL) + || v->dir_next != NULL)) return EPERM; - } // remove it from the global hash table hash_remove(fs->vnode_list_hash, v); // TK: for partitions, we have to release the raw device - if( v->stream.type == STREAM_TYPE_DEVICE && v->stream.u.dev.part_map ) - vfs_put_vnode( fs->id, v->stream.u.dev.part_map->raw_vnode->id ); - - if(v->name != NULL) + if (v->stream.type == STREAM_TYPE_DEVICE && v->stream.u.dev.part_map) + vfs_put_vnode(fs->id, v->stream.u.dev.part_map->raw_vnode->id); + + if (v->name != NULL) kfree(v->name); kfree(v); @@ -198,10 +201,9 @@ update_dircookies(struct devfs_vnode *dir, struct devfs_vnode *v) { struct devfs_cookie *cookie; - for(cookie = dir->stream.u.dir.jar_head; cookie; cookie = cookie->u.dir.next) { - if(cookie->u.dir.ptr == v) { + for (cookie = dir->stream.u.dir.jar_head; cookie; cookie = cookie->u.dir.next) { + if (cookie->u.dir.ptr == v) cookie->u.dir.ptr = v->dir_next; - } } } @@ -211,18 +213,18 @@ devfs_find_in_dir(struct devfs_vnode *dir, const char *path) { struct devfs_vnode *v; - if(dir->stream.type != STREAM_TYPE_DIR) + if (dir->stream.type != STREAM_TYPE_DIR) return NULL; - if(!strcmp(path, ".")) + if (!strcmp(path, ".")) return dir; - if(!strcmp(path, "..")) + if (!strcmp(path, "..")) return dir->parent; - for(v = dir->stream.u.dir.dir_head; v; v = v->dir_next) { -// dprintf("devfs_find_in_dir: looking at entry '%s'\n", v->name); - if(strcmp(v->name, path) == 0) { -// dprintf("devfs_find_in_dir: found it at 0x%x\n", v); + for (v = dir->stream.u.dir.dir_head; v; v = v->dir_next) { + INSANE(("devfs_find_in_dir: looking at entry '%s'\n", v->name)); + if (strcmp(v->name, path) == 0) { + INSANE(("devfs_find_in_dir: found it at %p\n", v)); return v; } } @@ -233,7 +235,7 @@ devfs_find_in_dir(struct devfs_vnode *dir, const char *path) static int devfs_insert_in_dir(struct devfs_vnode *dir, struct devfs_vnode *v) { - if(dir->stream.type != STREAM_TYPE_DIR) + if (dir->stream.type != STREAM_TYPE_DIR) return EINVAL; v->dir_next = dir->stream.u.dir.dir_head; @@ -250,12 +252,12 @@ devfs_remove_from_dir(struct devfs_vnode *dir, struct devfs_vnode *findit) struct devfs_vnode *v; struct devfs_vnode *last_v; - for(v = dir->stream.u.dir.dir_head, last_v = NULL; v; last_v = v, v = v->dir_next) { - if(v == findit) { + for (v = dir->stream.u.dir.dir_head, last_v = NULL; v; last_v = v, v = v->dir_next) { + if (v == findit) { /* make sure all dircookies dont point to this vnode */ update_dircookies(dir, v); - if(last_v) + if (last_v) last_v->dir_next = v->dir_next; else dir->stream.u.dir.dir_head = v->dir_next; @@ -270,8 +272,9 @@ devfs_remove_from_dir(struct devfs_vnode *dir, struct devfs_vnode *findit) static int devfs_is_dir_empty(struct devfs_vnode *dir) { - if(dir->stream.type != STREAM_TYPE_DIR) + if (dir->stream.type != STREAM_TYPE_DIR) return false; + return !dir->stream.u.dir.dir_head; } @@ -282,8 +285,8 @@ devfs_get_partition_info( struct devfs *fs, struct devfs_vnode *v, { devfs_partition_info *info = (devfs_partition_info *)buf; struct devfs_part_map *part_map = v->stream.u.dev.part_map; - - if( v->stream.type != STREAM_TYPE_DEVICE || part_map == NULL ) + + if (v->stream.type != STREAM_TYPE_DEVICE || part_map == NULL) return EINVAL; info->offset = part_map->offset; @@ -310,20 +313,20 @@ static int devfs_set_partition( struct devfs *fs, struct devfs_vnode *v, info = *(devfs_partition_info *)buf; - if( v->stream.type != STREAM_TYPE_DEVICE ) + if (v->stream.type != STREAM_TYPE_DEVICE) return EINVAL; // we don't support nested partitions - if( v->stream.u.dev.part_map ) + if (v->stream.u.dev.part_map) return EINVAL; // reduce checks to a minimum - things like negative offsets could be useful - if( info.size < 0) + if (info.size < 0) return EINVAL; // create partition map - part_map = kmalloc( sizeof( *part_map )); - if( !part_map ) + part_map = kmalloc(sizeof(*part_map)); + if (!part_map) return ENOMEM; part_map->offset = info.offset; @@ -332,12 +335,12 @@ static int devfs_set_partition( struct devfs *fs, struct devfs_vnode *v, part_map->session = info.session; part_map->partition = info.partition; - sprintf( part_name, "%i_%i", info.session, info.partition ); + sprintf(part_name, "%i_%i", info.session, info.partition); - mutex_lock(&thedevfs->lock); + mutex_lock(&gDeviceFileSystem->lock); // you cannot change a partition once set - if( devfs_find_in_dir( v->parent, part_name )) { + if (devfs_find_in_dir( v->parent, part_name)) { res = EINVAL; goto err1; } @@ -345,14 +348,14 @@ static int devfs_set_partition( struct devfs *fs, struct devfs_vnode *v, // increase reference count of raw device - // the partition device really needs it // (at least to resolve its name on GET_PARTITION_INFO) - res = vfs_get_vnode( fs->id, v->id, (fs_vnode *)&part_map->raw_vnode ); - if( res < 0 ) + res = vfs_get_vnode(fs->id, v->id, (fs_vnode *)&part_map->raw_vnode); + if (res < 0) goto err1; // now create the partition node - part_node = devfs_create_vnode( fs, part_name ); + part_node = devfs_create_vnode(fs, part_name); - if( part_node == NULL ) { + if (part_node == NULL) { res = ENOMEM; goto err2; } @@ -362,27 +365,27 @@ static int devfs_set_partition( struct devfs *fs, struct devfs_vnode *v, part_node->stream.u.dev.calls = v->stream.u.dev.calls; part_node->stream.u.dev.part_map = part_map; - hash_insert( fs->vnode_list_hash, part_node ); + hash_insert(fs->vnode_list_hash, part_node); - devfs_insert_in_dir( v->parent, part_node ); + devfs_insert_in_dir(v->parent, part_node); - mutex_unlock(&thedevfs->lock); + mutex_unlock(&gDeviceFileSystem->lock); - dprintf( "SET_PARTITION: Added partition\n" ); + TRACE(("SET_PARTITION: Added partition\n")); return B_NO_ERROR; err1: - mutex_unlock(&thedevfs->lock); + mutex_unlock(&gDeviceFileSystem->lock); - kfree( part_map ); + kfree(part_map); return res; err2: - mutex_unlock(&thedevfs->lock); + mutex_unlock(&gDeviceFileSystem->lock); - vfs_put_vnode( fs->id, v->id ); - kfree( part_map ); + vfs_put_vnode(fs->id, v->id); + kfree(part_map); return res; } @@ -399,7 +402,7 @@ devfs_mount(fs_cookie *_fs, fs_id id, const char *devfs, void *args, vnode_id *r TRACE(("devfs_mount: entry\n")); - if (thedevfs) { + if (gDeviceFileSystem) { dprintf("double mount of devfs attempted\n"); err = ERR_GENERAL; goto err; @@ -447,7 +450,7 @@ devfs_mount(fs_cookie *_fs, fs_id id, const char *devfs, void *args, vnode_id *r *root_vnid = v->id; *_fs = fs; - thedevfs = fs; + gDeviceFileSystem = fs; return 0; @@ -470,7 +473,7 @@ devfs_unmount(fs_cookie _fs) struct devfs_vnode *v; struct hash_iterator i; - TRACE(("devfs_unmount: entry fs = 0x%x\n", fs)); + TRACE(("devfs_unmount: entry fs = %p\n", fs)); // delete all of the vnodes hash_open(fs->vnode_list_hash, &i); @@ -501,71 +504,69 @@ devfs_lookup(fs_cookie _fs, fs_vnode _dir, const char *name, vnode_id *id) { struct devfs *fs = (struct devfs *)_fs; struct devfs_vnode *dir = (struct devfs_vnode *)_dir; - struct devfs_vnode *v; - struct devfs_vnode *v1; + struct devfs_vnode *vnode; + struct devfs_vnode *vdummy; int err; - TRACE(("devfs_lookup: entry dir 0x%x, name '%s'\n", dir, name)); + TRACE(("devfs_lookup: entry dir %p, name '%s'\n", dir, name)); - if(dir->stream.type != STREAM_TYPE_DIR) + if (dir->stream.type != STREAM_TYPE_DIR) return ENOTDIR; mutex_lock(&fs->lock); // look it up - v = devfs_find_in_dir(dir, name); - if(!v) { + vnode = devfs_find_in_dir(dir, name); + if (!vnode) { err = ERR_NOT_FOUND; goto err; } - err = vfs_get_vnode(fs->id, v->id, (fs_vnode *)&v1); - if(err < 0) { + err = vfs_get_vnode(fs->id, vnode->id, (fs_vnode *)&vdummy); + if (err < 0) goto err; - } - *id = v->id; - - err = B_NO_ERROR; + *id = vnode->id; err: mutex_unlock(&fs->lock); + INSANE(("--devfs_lookup: returns %d\n",err)); return err; } static int -devfs_get_vnode(fs_cookie _fs, vnode_id id, fs_vnode *v, bool r) +devfs_get_vnode(fs_cookie _fs, vnode_id id, fs_vnode *_vnode, bool reenter) { struct devfs *fs = (struct devfs *)_fs; - TRACE(("devfs_getvnode: asking for vnode 0x%x 0x%x, r %d\n", id, r)); + TRACE(("devfs_get_vnode: asking for vnode id = %Ld, vnode = %p, r %d\n", id, _vnode, reenter)); - if(!r) + if (!reenter) mutex_lock(&fs->lock); - *v = hash_lookup(fs->vnode_list_hash, &id); + *_vnode = hash_lookup(fs->vnode_list_hash, &id); - if(!r) + if (!reenter) mutex_unlock(&fs->lock); - TRACE(("devfs_getnvnode: looked it up at 0x%x\n", *v)); + TRACE(("devfs_get_vnode: looked it up at %p\n", *_vnode)); - if(*v) + if (*_vnode) return 0; - else - return ERR_NOT_FOUND; + + return ERR_NOT_FOUND; } static int -devfs_put_vnode(fs_cookie _fs, fs_vnode _v, bool r) +devfs_put_vnode(fs_cookie _fs, fs_vnode _v, bool reenter) { #if DEVFS_TRACE - struct devfs_vnode *v = (struct devfs_vnode *)_v; + struct devfs_vnode *vnode = (struct devfs_vnode *)_v; - TRACE(("devfs_putvnode: entry on vnode 0x%x 0x%x, r %d\n", v->id, r)); + TRACE(("devfs_put_vnode: entry on vnode %p, id = %Ld, reenter %d\n", vnode, vnode->id, reenter)); #endif return 0; // whatever @@ -573,30 +574,27 @@ devfs_put_vnode(fs_cookie _fs, fs_vnode _v, bool r) static int -devfs_remove_vnode(fs_cookie _fs, fs_vnode _v, bool r) +devfs_remove_vnode(fs_cookie _fs, fs_vnode _v, bool reenter) { struct devfs *fs = (struct devfs *)_fs; - struct devfs_vnode *v = (struct devfs_vnode *)_v; - int err; + struct devfs_vnode *vnode = (struct devfs_vnode *)_v; - TRACE(("devfs_removevnode: remove 0x%x (0x%x 0x%x), r %d\n", v, v->id, r)); + TRACE(("devfs_removevnode: remove %p (%Ld), reenter %d\n", vnode, vnode->id, reenter)); - if(!r) + if (!reenter) mutex_lock(&fs->lock); - if(v->dir_next) { + if (vnode->dir_next) { // can't remove node if it's linked to the dir - panic("devfs_removevnode: vnode %p asked to be removed is present in dir\n", v); + panic("devfs_removevnode: vnode %p asked to be removed is present in dir\n", vnode); } - devfs_delete_vnode(fs, v, false); + devfs_delete_vnode(fs, vnode, false); - err = 0; - - if(!r) + if (!reenter) mutex_unlock(&fs->lock); - return err; + return B_OK; } @@ -615,14 +613,25 @@ devfs_open(fs_cookie _fs, fs_vnode _v, file_cookie *_cookie, int oflags) struct devfs_cookie *cookie; int status = 0; - TRACE(("devfs_open: vnode 0x%x, oflags 0x%x\n", v, oflags)); + TRACE(("devfs_open: vnode %p, oflags 0x%x\n", vnode, oflags)); cookie = kmalloc(sizeof(struct devfs_cookie)); if (cookie == NULL) return ENOMEM; + INSANE(("zulu: calls = %p\n",vnode->stream.u.dev.calls)); + if (vnode->stream.u.dev.calls) + INSANE(("hellacious: open = %p!\n",vnode->stream.u.dev.calls->open)); + + if (vnode->stream.type != STREAM_TYPE_DEVICE) { + INSANE(("bye bye!\n")); + return EINVAL; + } + INSANE(("got here.\n")); + status = vnode->stream.u.dev.calls->open(vnode->name, oflags, &cookie->u.dev.dcookie); *_cookie = cookie; + INSANE(("cool!\n")); return status; } @@ -634,7 +643,7 @@ devfs_close(fs_cookie _fs, fs_vnode _v, file_cookie _cookie) struct devfs_vnode *vnode = _v; struct devfs_cookie *cookie = _cookie; - TRACE(("devfs_close: entry vnode 0x%x, cookie 0x%x\n", v, cookie)); + TRACE(("devfs_close: entry vnode %p, cookie %p\n", vnode, cookie)); if (vnode->stream.type == STREAM_TYPE_DEVICE) { // pass the call through to the underlying device @@ -651,7 +660,7 @@ devfs_free_cookie(fs_cookie _fs, fs_vnode _v, file_cookie _cookie) struct devfs_vnode *vnode = _v; struct devfs_cookie *cookie = _cookie; - TRACE(("devfs_freecookie: entry vnode 0x%x, cookie 0x%x\n", vnode, cookie)); + TRACE(("devfs_freecookie: entry vnode %p, cookie %p\n", vnode, cookie)); if (vnode->stream.type == STREAM_TYPE_DEVICE) { // pass the call through to the underlying device @@ -679,15 +688,19 @@ devfs_read(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, void *buffer, off_t struct devfs_vnode *vnode = _v; struct devfs_cookie *cookie = _cookie; struct devfs_part_map *part_map; + int status; - TRACE(("devfs_read: vnode 0x%x, cookie 0x%x, pos 0x%x 0x%x, len 0x%x\n", vnode, cookie, pos, len)); + TRACE(("devfs_read: vnode %p, cookie %p, pos %Ld, len %p\n", vnode, cookie, pos, length)); - if (cookie->s->type != STREAM_TYPE_DEVICE) - return EINVAL; +INSANE(("juchu, buffer = %p!\n",buffer)); +// if (cookie->stream->type != STREAM_TYPE_DEVICE) +// return EINVAL; +INSANE((":%p:%p:%p:%p\n",vnode->all_next,vnode->name,vnode->redir_vnode,vnode->parent)); +INSANE(("name = %s\n",vnode->name)); part_map = vnode->stream.u.dev.part_map; if (part_map) { - if( pos < 0 ) + if (pos < 0) pos = 0; if (pos > part_map->size) @@ -698,7 +711,11 @@ devfs_read(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, void *buffer, off_t } // pass the call through to the device - return vnode->stream.u.dev.calls->read(cookie->u.dev.dcookie, pos, buffer, length); + INSANE(("calls = %p\n",vnode->stream.u.dev.calls)); + status = vnode->stream.u.dev.calls->read(cookie->u.dev.dcookie, pos, buffer, length); + INSANE(("hulu: calls = %p\n",vnode->stream.u.dev.calls)); + INSANE((":%p:%p:%p:%p\n",vnode->all_next,vnode->name,vnode->redir_vnode,vnode->parent)); + return status; } @@ -706,13 +723,15 @@ static ssize_t devfs_write(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, const void *buf, off_t pos, size_t *len) { - struct devfs_vnode *v = _v; + struct devfs_vnode *vnode = _v; struct devfs_cookie *cookie = _cookie; - TRACE(("devfs_write: vnode 0x%x, cookie 0x%x, pos 0x%x 0x%x, len 0x%x\n", v, cookie, pos, len)); + TRACE(("devfs_write: vnode %p, cookie %p, pos %Ld, len %p\n", vnode, cookie, pos, len)); + INSANE((":%p:%p:%p:%p\n",vnode->all_next,vnode->name,vnode->redir_vnode,vnode->parent)); - if (v->stream.type == STREAM_TYPE_DEVICE) { - struct devfs_part_map *part_map = v->stream.u.dev.part_map; + if (vnode->stream.type == STREAM_TYPE_DEVICE) { + struct devfs_part_map *part_map = vnode->stream.u.dev.part_map; + int written; if (part_map) { if (pos < 0) @@ -725,51 +744,28 @@ devfs_write(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, const void *buf, pos += part_map->offset; } - return v->stream.u.dev.calls->write(cookie->u.dev.dcookie, pos, buf, len); + INSANE(("hela: name = \"%s\", calls = %p\n",vnode->name,vnode->stream.u.dev.calls)); + written = vnode->stream.u.dev.calls->write(cookie->u.dev.dcookie, pos, buf, len); + INSANE(("helu: calls = %p\n",vnode->stream.u.dev.calls)); + INSANE((":%p:%p:%p:%p\n",vnode->all_next,vnode->name,vnode->redir_vnode,vnode->parent)); + return written; } - return EROFS; + return EINVAL; } -static int -devfs_seek(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, off_t pos, int st) +static off_t +devfs_seek(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, off_t pos, int seekType) { +#ifdef DEBUG struct devfs *fs = _fs; - struct devfs_vnode *v = _v; + struct devfs_vnode *vnode = _v; struct devfs_cookie *cookie = _cookie; - int err = 0; - TRACE(("devfs_seek: vnode 0x%x, cookie 0x%x, pos 0x%x 0x%x, seek_type %d\n", v, cookie, pos, st)); + TRACE(("devfs_seek: vnode %p, cookie %p, pos %Ld, seekType %d\n", vnode, cookie, pos, seekType)); +#endif - switch(cookie->s->type) { - case STREAM_TYPE_DIR: - mutex_lock(&fs->lock); - switch(st) { - // only valid args are seek_type SEEK_SET, pos 0. - // this rewinds to beginning of directory - case SEEK_SET: - if(pos == 0) { - cookie->u.dir.ptr = cookie->s->u.dir.dir_head; - } else { - err = ESPIPE; - } - break; - case SEEK_CUR: - case SEEK_END: - default: - err = EINVAL; - } - mutex_unlock(&fs->lock); - break; - case STREAM_TYPE_DEVICE: - dprintf("seek not supported!\n"); - //err = v->stream.u.dev.calls->dev_seek(cookie->u.dev.dcookie, pos, st); - break; - default: - err = EINVAL; - } - - return err; + return ESPIPE; } @@ -787,7 +783,7 @@ devfs_open_dir(fs_cookie _fs, fs_vnode _v, file_cookie *_cookie) struct devfs_vnode *vnode = _v; struct devfs_cookie *cookie; - TRACE(("devfs_open: vnode 0x%x, oflags 0x%x\n", vnode, oflags)); + TRACE(("devfs_open_dir: vnode %p\n", vnode)); if (vnode->stream.type != STREAM_TYPE_DIR) return EINVAL; @@ -798,7 +794,7 @@ devfs_open_dir(fs_cookie _fs, fs_vnode _v, file_cookie *_cookie) mutex_lock(&fs->lock); - cookie->s = &vnode->stream; + cookie->stream = &vnode->stream; cookie->u.dir.ptr = vnode->stream.u.dir.dir_head; *_cookie = cookie; @@ -814,7 +810,10 @@ devfs_read_dir(fs_cookie _fs, fs_vnode _vnode, file_cookie _cookie, struct diren struct devfs *fs = _fs; status_t status = 0; - TRACE(("devfs_read_dir: vnode 0x%x, cookie 0x%x, pos 0x%x 0x%x, len 0x%x\n", v, cookie, dirent, bufferSize)); + TRACE(("devfs_read_dir: vnode %p, cookie %p, buffer %p, size %ld\n", _vnode, cookie, dirent, bufferSize)); + + if (cookie->stream->type != STREAM_TYPE_DIR) + return EINVAL; mutex_lock(&fs->lock); @@ -850,12 +849,16 @@ static int devfs_rewind_dir(fs_cookie _fs, fs_vnode _vnode, file_cookie _cookie) { struct devfs *fs = _fs; - struct devfs_vnode *vnode = _vnode; struct devfs_cookie *cookie = _cookie; + + TRACE(("devfs_rewind_dir: vnode %p, cookie %p\n", _vnode, _cookie)); + + if (cookie->stream->type != STREAM_TYPE_DIR) + return EINVAL; mutex_lock(&fs->lock); - cookie->u.dir.ptr = vnode->stream.u.dir.dir_head; + cookie->u.dir.ptr = cookie->stream->u.dir.dir_head; mutex_unlock(&fs->lock); return B_OK; @@ -869,15 +872,15 @@ devfs_ioctl(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, ulong op, void *buf struct devfs_vnode *v = _v; struct devfs_cookie *cookie = _cookie; - TRACE(("devfs_ioctl: vnode 0x%x, cookie 0x%x, op %d, buf 0x%x, len 0x%x\n", _v, _cookie, op, buf, len)); + TRACE(("devfs_ioctl: vnode %p, cookie %p, op %ld, buf %p, len %ld\n", _v, _cookie, op, buf, len)); if (v->stream.type == STREAM_TYPE_DEVICE) { switch (op) { case IOCTL_DEVFS_GET_PARTITION_INFO: - return devfs_get_partition_info( fs, v, cookie, buf, len ); + return devfs_get_partition_info(fs, v, cookie, buf, len); case IOCTL_DEVFS_SET_PARTITION: - return devfs_set_partition( fs, v, cookie, buf, len ); + return devfs_set_partition(fs, v, cookie, buf, len); } return v->stream.u.dev.calls->control(cookie->u.dev.dcookie, op, buf, len); @@ -1008,15 +1011,16 @@ devfs_rename(fs_cookie _fs, fs_vnode _olddir, const char *oldname, fs_vnode _new static int devfs_read_stat(fs_cookie _fs, fs_vnode _v, struct stat *stat) { - struct devfs_vnode *v = _v; + struct devfs_vnode *vnode = _v; - TRACE(("devfs_rstat: vnode 0x%x (0x%x 0x%x), stat 0x%x\n", v, v->id, stat)); + TRACE(("devfs_rstat: vnode %p (%Ld), stat %p\n", vnode, vnode->id, stat)); + INSANE(("-> calls = %p\n",vnode->stream.u.dev.calls)); - stat->st_ino = v->id; + stat->st_ino = vnode->id; stat->st_mode = DEFFILEMODE; stat->st_size = 0; - - if (v->stream.type == STREAM_TYPE_DIR) + + if (vnode->stream.type == STREAM_TYPE_DIR) stat->st_mode |= S_IFDIR; else stat->st_mode |= S_IFCHR; @@ -1031,7 +1035,7 @@ devfs_write_stat(fs_cookie _fs, fs_vnode _v, struct stat *stat, int stat_mask) #if DEVFS_TRACE struct devfs_vnode *v = _v; - TRACE(("devfs_wstat: vnode 0x%x (0x%x 0x%x), stat 0x%x\n", v, v->id, stat)); + TRACE(("devfs_wstat: vnode %p (%Ld), stat %p\n", v, v->id, stat)); #endif // cannot change anything return EPERM; @@ -1089,7 +1093,7 @@ int bootstrap_devfs(void) { - dprintf("bootstrap_devfs: entry\n"); + TRACE(("bootstrap_devfs: entry\n")); return vfs_register_filesystem("devfs", &devfs_calls); } @@ -1105,9 +1109,14 @@ devfs_publish_device(const char *path, void *ident, device_hooks *calls) struct devfs_vnode *v; bool at_leaf; - TRACE(("devfs_publish_device: entry path '%s', hooks 0x%x\n", path, calls)); + TRACE(("devfs_publish_device: entry path '%s', ident %p, hooks %p\n", path, ident, calls)); - if (!thedevfs) { + if (calls == NULL || path == NULL) { + panic("devfs_publish_device called with NULL pointer!\n"); + return EINVAL; + } + + if (!gDeviceFileSystem) { panic("devfs_publish_device called before devfs mounted\n"); return ERR_GENERAL; } @@ -1116,16 +1125,16 @@ devfs_publish_device(const char *path, void *ident, device_hooks *calls) strncpy(temp, path, SYS_MAX_PATH_LEN); temp[SYS_MAX_PATH_LEN] = 0; - mutex_lock(&thedevfs->lock); + mutex_lock(&gDeviceFileSystem->lock); // create the path leading to the device // parse the path passed in, stripping out '/' - dir = thedevfs->root_vnode; + dir = gDeviceFileSystem->root_vnode; v = NULL; i = 0; last = 0; at_leaf = false; - for(;;) { + for (;;) { if(temp[i] == 0) { at_leaf = true; // we'll be done after this one } else if(temp[i] == '/') { @@ -1141,10 +1150,10 @@ devfs_publish_device(const char *path, void *ident, device_hooks *calls) // we have a path component v = devfs_find_in_dir(dir, &temp[last]); if (v) { - if(!at_leaf) { + if (!at_leaf) { // we are not at the leaf of the path, so as long as // this is a dir we're okay - if(v->stream.type == STREAM_TYPE_DIR) { + if (v->stream.type == STREAM_TYPE_DIR) { last = i; dir = v; continue; @@ -1156,8 +1165,8 @@ devfs_publish_device(const char *path, void *ident, device_hooks *calls) err = ERR_VFS_ALREADY_EXISTS; goto err; } else { - v = devfs_create_vnode(thedevfs, &temp[last]); - if(!v) { + v = devfs_create_vnode(gDeviceFileSystem, &temp[last]); + if (!v) { err = ENOMEM; goto err; } @@ -1176,7 +1185,7 @@ devfs_publish_device(const char *path, void *ident, device_hooks *calls) v->stream.u.dir.jar_head = NULL; } - hash_insert(thedevfs->vnode_list_hash, v); + hash_insert(gDeviceFileSystem->vnode_list_hash, v); devfs_insert_in_dir(dir, v); @@ -1187,7 +1196,7 @@ devfs_publish_device(const char *path, void *ident, device_hooks *calls) } err: - mutex_unlock(&thedevfs->lock); + mutex_unlock(&gDeviceFileSystem->lock); return err; } diff --git a/src/kernel/core/fs/rootfs.c b/src/kernel/core/fs/rootfs.c index 1319750cb2..806e2bf4b6 100755 --- a/src/kernel/core/fs/rootfs.c +++ b/src/kernel/core/fs/rootfs.c @@ -112,12 +112,12 @@ rootfs_delete_vnode(struct rootfs *fs, struct rootfs_vnode *v, bool force_delete // cant delete it if it's in a directory or is a directory // and has children if (!force_delete && (v->stream.dir.dir_head != NULL || v->dir_next != NULL)) - return ERR_NOT_ALLOWED; + return EPERM; // remove it from the global hash table hash_remove(fs->vnode_list_hash, v); - if(v->name != NULL) + if (v->name != NULL) kfree(v->name); kfree(v); @@ -221,10 +221,8 @@ rootfs_mount(fs_cookie *_fs, fs_id id, const char *device, void *args, vnode_id TRACE(("rootfs_mount: entry\n")); fs = kmalloc(sizeof(struct rootfs)); - if(fs == NULL) { - err = ERR_NO_MEMORY; - goto err; - } + if (fs == NULL) + return ENOMEM; fs->id = id; fs->next_vnode_id = 0; @@ -236,23 +234,23 @@ rootfs_mount(fs_cookie *_fs, fs_id id, const char *device, void *args, vnode_id fs->vnode_list_hash = hash_init(ROOTFS_HASH_SIZE, (addr)&v->all_next - (addr)v, &rootfs_vnode_compare_func, &rootfs_vnode_hash_func); - if(fs->vnode_list_hash == NULL) { - err = ERR_NO_MEMORY; + if (fs->vnode_list_hash == NULL) { + err = ENOMEM; goto err2; } // create a vnode v = rootfs_create_vnode(fs); - if(v == NULL) { - err = ERR_NO_MEMORY; + if (v == NULL) { + err = ENOMEM; goto err3; } // set it up v->parent = v; v->name = kstrdup(""); - if(v->name == NULL) { - err = ERR_NO_MEMORY; + if (v->name == NULL) { + err = ENOMEM; goto err4; } @@ -273,7 +271,7 @@ err2: mutex_destroy(&fs->lock); err1: kfree(fs); -err: + return err; } @@ -357,20 +355,20 @@ rootfs_get_vnode(fs_cookie _fs, vnode_id id, fs_vnode *v, bool r) TRACE(("rootfs_getvnode: asking for vnode 0x%x 0x%x, r %d\n", id, r)); - if(!r) + if (!r) mutex_lock(&fs->lock); *v = hash_lookup(fs->vnode_list_hash, &id); - if(!r) + if (!r) mutex_unlock(&fs->lock); TRACE(("rootfs_getnvnode: looked it up at 0x%x\n", *v)); - if(*v) - return 0; - else - return ERR_NOT_FOUND; + if (*v) + return B_NO_ERROR; + + return ENOENT; } @@ -477,41 +475,14 @@ rootfs_write(fs_cookie fs, fs_vnode v, file_cookie cookie, const void *buf, off_ { TRACE(("rootfs_write: vnode 0x%x, cookie 0x%x, pos 0x%x 0x%x, len 0x%x\n", v, cookie, pos, *len)); - return ERR_NOT_ALLOWED; + return EPERM; } -static int +static off_t rootfs_seek(fs_cookie _fs, fs_vnode _v, file_cookie _cookie, off_t pos, int st) { - struct rootfs *fs = _fs; - struct rootfs_vnode *v = _v; - struct rootfs_cookie *cookie = _cookie; - int err = 0; - - TRACE(("rootfs_seek: vnode 0x%x, cookie 0x%x, pos 0x%x 0x%x, seek_type %d\n", v, cookie, pos, st)); - - mutex_lock(&fs->lock); - - switch(st) { - // only valid args are seek_type SEEK_SET, pos 0. - // this rewinds to beginning of directory - case SEEK_SET: - if(pos == 0) { - cookie->ptr = v->stream.dir.dir_head; - } else { - err = ESPIPE; - } - break; - case SEEK_CUR: - case SEEK_END: - default: - err = EINVAL; - } - - mutex_unlock(&fs->lock); - - return err; + return ESPIPE; } diff --git a/src/kernel/core/fs/vfs.c b/src/kernel/core/fs/vfs.c index e2d3414abc..90e3d9aae7 100755 --- a/src/kernel/core/fs/vfs.c +++ b/src/kernel/core/fs/vfs.c @@ -108,15 +108,16 @@ static int vfs_close(struct file_descriptor *, int, struct io_context *); static int common_ioctl(struct file_descriptor *, ulong, void *buf, size_t len); static int common_read_stat(struct file_descriptor *, struct stat *); -static int common_close(struct file_descriptor *, int, struct io_context *); static ssize_t file_read(struct file_descriptor *, void *, off_t, size_t *); static ssize_t file_write(struct file_descriptor *, const void *, off_t, size_t *); -static int file_seek(struct file_descriptor *, off_t pos, int seek_type); +static off_t file_seek(struct file_descriptor *, off_t pos, int seek_type); static status_t dir_read(struct file_descriptor *,struct dirent *buffer,size_t bufferSize,uint32 *_count); static status_t dir_rewind(struct file_descriptor *); static void file_free_fd(struct file_descriptor *); +static int file_close(struct file_descriptor *); static void dir_free_fd(struct file_descriptor *); +static int dir_close(struct file_descriptor *); static int vfs_open(char *path, int omode, bool kernel); static int vfs_open_dir(char *path, bool kernel); @@ -132,7 +133,7 @@ struct fd_ops file_ops = { NULL, NULL, common_read_stat, - common_close, + file_close, file_free_fd }; @@ -145,7 +146,7 @@ struct fd_ops dir_ops = { dir_read, dir_rewind, common_read_stat, - common_close, + dir_close, dir_free_fd }; @@ -165,10 +166,10 @@ mount_compare(void *_m, const void *_key) struct fs_mount *mount = _m; const fs_id *id = _key; - if(mount->id == *id) + if (mount->id == *id) return 0; - else - return -1; + + return -1; } @@ -178,10 +179,10 @@ mount_hash(void *_m, const void *_key, unsigned int range) struct fs_mount *mount = _m; const fs_id *id = _key; - if(mount) + if (mount) return mount->id % range; - else - return *id % range; + + return *id % range; } @@ -312,7 +313,7 @@ dec_vnode_ref_count(struct vnode *v, bool free_mem, bool r) old_ref = atomic_add(&v->ref_count, -1); - PRINT(("dec_vnode_ref_count: vnode 0x%x, ref now %d\n", v, v->ref_count)); + PRINT(("dec_vnode_ref_count: vnode 0x%p, ref now %d\n", v, v->ref_count)); if (old_ref == 1) { v->busy = true; @@ -350,7 +351,7 @@ static int inc_vnode_ref_count(struct vnode *v) { atomic_add(&v->ref_count, 1); - PRINT(("inc_vnode_ref_count: vnode 0x%x, ref now %d\n", v, v->ref_count)); + PRINT(("inc_vnode_ref_count: vnode 0x%p, ref now %d\n", v, v->ref_count)); return 0; } @@ -373,7 +374,7 @@ get_vnode(fs_id fsid, vnode_id vnid, struct vnode **outv, int r) struct vnode *v; int err; - FUNCTION(("get_vnode: fsid %d vnid 0x%x 0x%x\n", fsid, vnid)); + FUNCTION(("get_vnode: fsid %d vnid 0x%Lx 0x%p\n", fsid, vnid,outv)); mutex_lock(&vfs_vnode_mutex); @@ -389,7 +390,7 @@ get_vnode(fs_id fsid, vnode_id vnid, struct vnode **outv, int r) } } while(0); - PRINT(("get_vnode: tried to lookup vnode, got 0x%x\n", v)); + PRINT(("get_vnode: tried to lookup vnode, got 0x%p\n", v)); if (v) { inc_vnode_ref_count(v); @@ -428,7 +429,7 @@ get_vnode(fs_id fsid, vnode_id vnid, struct vnode **outv, int r) mutex_unlock(&vfs_vnode_mutex); - PRINT(("get_vnode: returning 0x%x\n", v)); + PRINT(("get_vnode: returning 0x%p\n", v)); *outv = v; return B_NO_ERROR; @@ -486,7 +487,7 @@ vfs_put_vnode(fs_id fsid, vnode_id vnid) void vfs_vnode_acquire_ref(void *v) { - FUNCTION(("vfs_vnode_acquire_ref: vnode 0x%x\n", v)); + FUNCTION(("vfs_vnode_acquire_ref: vnode 0x%p\n", v)); inc_vnode_ref_count((struct vnode *)v); } @@ -494,7 +495,7 @@ vfs_vnode_acquire_ref(void *v) void vfs_vnode_release_ref(void *v) { - FUNCTION(("vfs_vnode_release_ref: vnode 0x%x\n", v)); + FUNCTION(("vfs_vnode_release_ref: vnode 0x%p\n", v)); dec_vnode_ref_count((struct vnode *)v, true, false); } @@ -538,7 +539,7 @@ file_free_fd(struct file_descriptor *descriptor) struct vnode *vnode = descriptor->vnode; if (vnode != NULL) { - FS_CALL(vnode,fs_close)(vnode->mount->cookie, vnode->priv_vnode, descriptor->cookie); + //FS_CALL(vnode,fs_close)(vnode->mount->cookie, vnode->priv_vnode, descriptor->cookie); FS_CALL(vnode,fs_free_cookie)(vnode->mount->cookie, vnode->priv_vnode, descriptor->cookie); dec_vnode_ref_count(vnode, true, false); } @@ -551,7 +552,7 @@ dir_free_fd(struct file_descriptor *descriptor) struct vnode *vnode = descriptor->vnode; if (vnode != NULL) { - FS_CALL(vnode,fs_close_dir)(vnode->mount->cookie, vnode->priv_vnode, descriptor->cookie); + //FS_CALL(vnode,fs_close_dir)(vnode->mount->cookie, vnode->priv_vnode, descriptor->cookie); FS_CALL(vnode,fs_free_dir_cookie)(vnode->mount->cookie, vnode->priv_vnode, descriptor->cookie); dec_vnode_ref_count(vnode, true, false); } @@ -942,26 +943,24 @@ vfs_mount(char *path, const char *device, const char *fs_name, void *args, bool struct vnode *covered_vnode = NULL; vnode_id root_id; -#if MAKE_NOIZE - dprintf("vfs_mount: entry. path = '%s', fs_name = '%s'\n", path, fs_name); -#endif + FUNCTION(("vfs_mount: entry. path = '%s', fs_name = '%s'\n", path, fs_name)); mutex_lock(&vfs_mount_op_mutex); mount = (struct fs_mount *)kmalloc(sizeof(struct fs_mount)); - if(mount == NULL) { + if (mount == NULL) { err = ENOMEM; goto err; } mount->mount_point = kstrdup(path); - if(mount->mount_point == NULL) { + if (mount->mount_point == NULL) { err = ENOMEM; goto err1; } mount->fs = find_fs(fs_name); - if(mount->fs == NULL) { + if (mount->fs == NULL) { err = ERR_VFS_INVALID_FS; goto err2; } @@ -972,13 +971,13 @@ vfs_mount(char *path, const char *device, const char *fs_name, void *args, bool if(!root_vnode) { // we haven't mounted anything yet - if(strcmp(path, "/") != 0) { + if (strcmp(path, "/") != 0) { err = ERR_VFS_GENERAL; goto err3; } err = mount->fs->calls->fs_mount(&mount->cookie, mount->id, device, NULL, &root_id); - if(err < 0) { + if (err < 0) { err = ERR_VFS_GENERAL; goto err3; } @@ -986,18 +985,17 @@ vfs_mount(char *path, const char *device, const char *fs_name, void *args, bool mount->covers_vnode = NULL; // this is the root mount } else { err = path_to_vnode(path,&covered_vnode,kernel); - if(err < 0) { + if (err < 0) goto err2; - } - if(!covered_vnode) { + if (!covered_vnode) { err = ERR_VFS_GENERAL; goto err2; } // XXX insert check to make sure covered_vnode is a DIR, or maybe it's okay for it not to be - if((covered_vnode != root_vnode) && (covered_vnode->mount->root_vnode == covered_vnode)){ + if ((covered_vnode != root_vnode) && (covered_vnode->mount->root_vnode == covered_vnode)){ err = ERR_VFS_ALREADY_MOUNTPOINT; goto err2; } @@ -1006,7 +1004,7 @@ vfs_mount(char *path, const char *device, const char *fs_name, void *args, bool // mount it err = mount->fs->calls->fs_mount(&mount->cookie, mount->id, device, NULL, &root_id); - if(err < 0) + if (err < 0) goto err4; } @@ -1018,14 +1016,14 @@ vfs_mount(char *path, const char *device, const char *fs_name, void *args, bool mutex_unlock(&vfs_mount_mutex); err = get_vnode(mount->id, root_id, &mount->root_vnode, 0); - if(err < 0) + if (err < 0) goto err5; // XXX may be a race here - if(mount->covers_vnode) + if (mount->covers_vnode) mount->covers_vnode->covered_by = mount->root_vnode; - if(!root_vnode) + if (!root_vnode) root_vnode = mount->root_vnode; mutex_unlock(&vfs_mount_op_mutex); @@ -1035,7 +1033,7 @@ vfs_mount(char *path, const char *device, const char *fs_name, void *args, bool err5: mount->fs->calls->fs_unmount(mount->cookie); err4: - if(mount->covers_vnode) + if (mount->covers_vnode) dec_vnode_ref_count(mount->covers_vnode, true, false); err3: recursive_lock_destroy(&mount->rlock); @@ -1057,12 +1055,10 @@ vfs_unmount(char *path, bool kernel) struct fs_mount *mount; int err; -#if MAKE_NOIZE - dprintf("vfs_unmount: entry. path = '%s', kernel %d\n", path, kernel); -#endif + FUNCTION(("vfs_unmount: entry. path = '%s', kernel %d\n", path, kernel)); err = path_to_vnode(path, &v, kernel); - if(err < 0) { + if (err < 0) { err = ERR_VFS_PATH_NOT_FOUND; goto err; } @@ -1070,11 +1066,10 @@ vfs_unmount(char *path, bool kernel) mutex_lock(&vfs_mount_op_mutex); mount = fsid_to_mount(v->fsid); - if(!mount) { + if (!mount) panic("vfs_unmount: fsid_to_mount failed on root vnode @%p of mount\n", v); - } - if(mount->root_vnode != v) { + if (mount->root_vnode != v) { // not mountpoint dec_vnode_ref_count(v, true, false); err = ERR_VFS_NOT_MOUNTPOINT; @@ -1147,16 +1142,14 @@ vfs_sync(void) struct hash_iterator iter; struct fs_mount *mount; -#if MAKE_NOIZE - dprintf("vfs_sync: entry.\n"); -#endif + FUNCTION(("vfs_sync: entry.\n")); /* cycle through and call sync on each mounted fs */ mutex_lock(&vfs_mount_op_mutex); mutex_lock(&vfs_mount_mutex); hash_open(mounts_table, &iter); - while((mount = hash_next(mounts_table, &iter))) { + while ((mount = hash_next(mounts_table, &iter))) { mount->fs->calls->fs_sync(mount->cookie); } hash_close(mounts_table, &iter, false); @@ -1200,7 +1193,7 @@ vfs_create(char *path, int omode, int perms, bool kernel) vnode_id newID; int status; - FUNCTION(("vfs_create: path '%s', kernel %d\n", path, stream_type, args, kernel)); + FUNCTION(("vfs_create: path '%s', omode %x, perms %d, kernel %d\n", path, omode, perms, kernel)); status = path_to_dir_vnode(path, &vnode, filename, kernel); if (status < 0) @@ -1270,13 +1263,30 @@ err: static int -common_close(struct file_descriptor *descriptor, int fd, struct io_context *io) +file_close(struct file_descriptor *descriptor) { - // We don't call fs_close() here, because a forked team might - // have access to the same fd - just remove it from our fd array - remove_fd(io, fd); + struct vnode *vnode = descriptor->vnode; - return 0; + FUNCTION(("file_close(descriptor = %p)\n",descriptor)); + + if (FS_CALL(vnode,fs_close)) + return FS_CALL(vnode,fs_close)(vnode->mount->cookie,vnode->priv_vnode,descriptor->cookie); + + return B_OK; +} + + +static int +dir_close(struct file_descriptor *descriptor) +{ + struct vnode *vnode = descriptor->vnode; + + FUNCTION(("dir_close(descriptor = %p)\n",descriptor)); + + if (FS_CALL(vnode,fs_close_dir)) + return FS_CALL(vnode,fs_close_dir)(vnode->mount->cookie,vnode->priv_vnode,descriptor->cookie); + + return B_OK; } @@ -1287,9 +1297,7 @@ vfs_fsync(int fd, bool kernel) struct vnode *v; int err; -#if MAKE_NOIZE - dprintf("vfs_fsync: entry. fd %d kernel %d\n", fd, kernel); -#endif + FUNCTION(("vfs_fsync: entry. fd %d kernel %d\n", fd, kernel)); f = get_fd(get_current_io_context(kernel), fd); if (!f) @@ -1309,8 +1317,7 @@ file_read(struct file_descriptor *f, void *buffer, off_t pos, size_t *length) { struct vnode *v = f->vnode; - FUNCTION(("vfs_read: fd = %d, buf 0x%x, pos 0x%x 0x%x, len 0x%x, kernel %d\n", fd, buffer, pos, length, kernel)); - + FUNCTION(("file_read: buf %p, pos %Ld, len 0x%p\n", buffer, pos, length)); return v->mount->fs->calls->fs_read(v->mount->cookie, v->priv_vnode, f->cookie, buffer, pos, length); } @@ -1320,20 +1327,19 @@ file_write(struct file_descriptor *f, const void *buffer, off_t pos, size_t *len { struct vnode *v = f->vnode; - FUNCTION(("vfs_write: fd = %d, buf 0x%x, pos 0x%x 0x%x, len 0x%x\n", fd, buffer, pos, length)); - + FUNCTION(("file_write: buf %p, pos %Ld, len 0x%p\n", buffer, pos, length)); return v->mount->fs->calls->fs_write(v->mount->cookie, v->priv_vnode, f->cookie, buffer, pos, length); } -static int -file_seek(struct file_descriptor *descriptor, off_t pos, int seek_type) +static off_t +file_seek(struct file_descriptor *descriptor, off_t pos, int seekType) { struct vnode *vnode = descriptor->vnode; - FUNCTION(("file_seek: fd = %d, pos 0x%x 0x%x, seek_type %d, kernel %d\n", fd, pos, seek_type, kernel)); + FUNCTION(("file_seek: pos 0x%Ld, seek_type %d\n", pos, seekType)); - return FS_CALL(vnode,fs_seek)(vnode->mount->cookie, vnode->priv_vnode, descriptor->cookie, pos, seek_type); + return FS_CALL(vnode,fs_seek)(vnode->mount->cookie, vnode->priv_vnode, descriptor->cookie, pos, seekType); } @@ -1370,7 +1376,7 @@ vfs_open_dir(char *path, bool kernel) int status; int fd; - FUNCTION(("vfs_open_dir: entry. path = '%s', omode %d, kernel %d\n", path, omode, kernel)); + FUNCTION(("vfs_open_dir: path = '%s', kernel %d\n", path, kernel)); status = path_to_vnode(path, &vnode, kernel); if (status < 0) @@ -1396,7 +1402,6 @@ vfs_open_dir(char *path, bool kernel) status = ERR_VFS_FD_TABLE_FULL; goto err1; } - return fd; err1: @@ -1505,8 +1510,7 @@ common_read_stat(struct file_descriptor *descriptor, struct stat *stat) { struct vnode *vnode = descriptor->vnode; - FUNCTION(("vfs_rstat: path '%s', stat 0x%x\n", path, stat)); - + FUNCTION(("common_read_stat: stat 0x%p\n", stat)); return FS_CALL(vnode,fs_read_stat)(vnode->mount->cookie, vnode->priv_vnode, stat); } @@ -1517,7 +1521,7 @@ vfs_write_stat(char *path, struct stat *stat, int stat_mask, bool kernel) struct vnode *vnode; int status; - FUNCTION(("vfs_wstat: path '%s', stat 0x%x, stat_mask %d, kernel %d\n", path, stat, stat_mask, kernel)); + FUNCTION(("vfs_write_stat: path '%s', stat 0x%p, stat_mask %d, kernel %d\n", path, stat, stat_mask, kernel)); status = path_to_vnode(path, &vnode, kernel); if (status < 0) @@ -1556,15 +1560,13 @@ vfs_get_vnode_from_path(const char *path, bool kernel, void **vnode) int err; char buf[SYS_MAX_PATH_LEN+1]; -#if MAKE_NOIZE - dprintf("vfs_get_vnode_from_path: entry. path = '%s', kernel %d\n", path, kernel); -#endif + PRINT(("vfs_get_vnode_from_path: entry. path = '%s', kernel %d\n", path, kernel)); strncpy(buf, path, SYS_MAX_PATH_LEN); buf[SYS_MAX_PATH_LEN] = 0; err = path_to_vnode(buf, &v, kernel); - if(err < 0) + if (err < 0) goto err; *vnode = v; @@ -1590,7 +1592,7 @@ vfs_can_page(void *_v) { struct vnode *vnode = _v; - FUNCTION(("vfs_canpage: vnode 0x%x\n", vnode)); + FUNCTION(("vfs_canpage: vnode 0x%p\n", vnode)); if (FS_CALL(vnode,fs_can_page)) return FS_CALL(vnode,fs_can_page)(vnode->mount->cookie, vnode->priv_vnode); @@ -1604,7 +1606,7 @@ vfs_read_page(void *_v, iovecs *vecs, off_t pos) { struct vnode *vnode = _v; - FUNCTION(("vfs_readpage: vnode 0x%x, vecs 0x%x, pos 0x%x 0x%x\n", vnode, vecs, pos)); + FUNCTION(("vfs_readpage: vnode %p, vecs %p, pos %Ld\n", vnode, vecs, pos)); return FS_CALL(vnode,fs_read_page)(vnode->mount->cookie, vnode->priv_vnode, vecs, pos); } @@ -1615,7 +1617,7 @@ vfs_write_page(void *_v, iovecs *vecs, off_t pos) { struct vnode *vnode = _v; - FUNCTION(("vfs_writepage: vnode 0x%x, vecs 0x%x, pos 0x%x 0x%x\n", vnode, vecs, pos)); + FUNCTION(("vfs_writepage: vnode %p, vecs %p, pos %Ld\n", vnode, vecs, pos)); return FS_CALL(vnode,fs_write_page)(vnode->mount->cookie, vnode->priv_vnode, vecs, pos); } @@ -1631,7 +1633,7 @@ vfs_get_cwd(char *buffer, size_t size, bool kernel) // Get current working directory from io context struct vnode *cwd = get_current_io_context(kernel)->cwd; - FUNCTION(("vfs_get_cwd: buf 0x%x, 0x%x\n", buffer, size)); + FUNCTION(("vfs_get_cwd: buf %p, size %ld\n", buffer, size)); if (cwd) // @@ -1707,9 +1709,7 @@ vfs_dup(int fd, bool kernel) struct file_descriptor *f; int rc; -#if MAKE_NOIZE - dprintf("vfs_dup: fd=%d\n", fd); -#endif + FUNCTION(("vfs_dup: fd = %d\n", fd)); // Try to get the fd structure f = get_fd(io, fd); @@ -1736,9 +1736,7 @@ vfs_dup2(int ofd, int nfd, bool kernel) struct file_descriptor *evicted; int rc; -#if MAKE_NOIZE - dprintf("vfs_dup2: ofd=%d nfd=%d\n", ofd, nfd); -#endif + FUNCTION(("vfs_dup2: ofd = %d, nfd = %d\n", ofd, nfd)); // quick check if ((ofd < 0) || (nfd < 0)) { @@ -1919,7 +1917,7 @@ sys_read_stat(const char *path, struct stat *stat) strncpy(buf, path, SYS_MAX_PATH_LEN); buf[SYS_MAX_PATH_LEN] = 0; - FUNCTION(("sys_rstat: path '%s', stat 0x%x,\n", path, stat)); + FUNCTION(("sys_read_stat: path '%s', stat %p,\n", path, stat)); status = path_to_vnode(buf, &vnode, true); if (status < 0) @@ -1950,9 +1948,7 @@ sys_getcwd(char *buf, size_t size) char path[SYS_MAX_PATH_LEN]; int rc; -#if MAKE_NOIZE - dprintf("sys_getcwd: buf 0x%x, 0x%x\n", buf, size); -#endif + PRINT(("sys_getcwd: buf %p, %ld\n", buf, size)); // Call vfs to get current working directory rc = vfs_get_cwd(path,SYS_MAX_PATH_LEN-1,true); @@ -1967,13 +1963,11 @@ sys_getcwd(char *buf, size_t size) int -sys_setcwd(const char* _path) +sys_setcwd(const char *_path) { char path[SYS_MAX_PATH_LEN]; -#if MAKE_NOIZE - dprintf("sys_setcwd: path=0x%x\n", _path); -#endif + PRINT(("sys_setcwd: path = %s\n", _path)); // Copy new path to kernel space strncpy(path, _path, SYS_MAX_PATH_LEN-1); @@ -2259,9 +2253,7 @@ user_getcwd(char *buf, size_t size) char path[SYS_MAX_PATH_LEN]; int rc, rc2; -#if MAKE_NOIZE - dprintf("user_getcwd: buf 0x%x, 0x%x\n", buf, size); -#endif + PRINT(("user_getcwd: buf %p, %ld\n", buf, size)); // Check if userspace address is inside "shared" kernel space if((addr)buf >= KERNEL_BASE && (addr)buf <= KERNEL_TOP) @@ -2282,14 +2274,12 @@ user_getcwd(char *buf, size_t size) int -user_setcwd(const char* upath) +user_setcwd(const char *upath) { char path[SYS_MAX_PATH_LEN]; int rc; -#if MAKE_NOIZE - dprintf("user_setcwd: path=0x%x\n", upath); -#endif + PRINT(("user_setcwd: path = %p\n", upath)); // Check if userspace address is inside "shared" kernel space if((addr)upath >= KERNEL_BASE && (addr)upath <= KERNEL_TOP) @@ -2297,9 +2287,9 @@ user_setcwd(const char* upath) // Copy new path to kernel space rc = user_strncpy(path, upath, SYS_MAX_PATH_LEN-1); - if (rc < 0) { + if (rc < 0) return rc; - } + path[SYS_MAX_PATH_LEN-1] = 0; // Call vfs to set new working directory @@ -2458,9 +2448,7 @@ vfs_test(void) sys_seek(fd, 0, SEEK_SET); for (;;) { len = sys_read(fd, buf, -1, sizeof(buf)); -// if(len <= 0) -// panic("readdir returned %Ld\n", (long long)len); - if(len > 0) + if (len > 0) dprintf("readdir returned name = '%s'\n", buf); else { dprintf("readdir returned %s\n", strerror(len)); @@ -2488,23 +2476,24 @@ vfs_test(void) #endif #if 1 - fd = sys_open("/boot", STREAM_TYPE_DIR, 0); + fd = sys_open_dir("/boot"); sys_close(fd); - fd = sys_open("/boot", STREAM_TYPE_DIR, 0); - if(fd < 0) + fd = sys_open_dir("/boot"); + if (fd < 0) panic("unable to open dir /boot\n"); { - char buf[64]; + char buf[256]; + struct dirent *dirent = (struct dirent *)buf; ssize_t len; - sys_seek(fd, 0, SEEK_SET); - for(;;) { - len = sys_read(fd, buf, -1, sizeof(buf)); + sys_rewind_dir(fd); + for (;;) { + len = sys_read_dir(fd, dirent, sizeof(buf), 1); // if(len < 0) // panic("readdir returned %Ld\n", (long long)len); - if(len > 0) - dprintf("sys_read returned name = '%s'\n", buf); + if (len > 0) + dprintf("sys_read returned name = '%s'\n", dirent->d_name); else { dprintf("sys_read returned %s\n", strerror(len)); break; @@ -2513,15 +2502,15 @@ vfs_test(void) } sys_close(fd); - fd = sys_open("/boot/kernel", STREAM_TYPE_FILE, 0); - if(fd < 0) + fd = sys_open("/boot/kernel", O_RDONLY); + if (fd < 0) panic("unable to open kernel file '/boot/kernel'\n"); { char buf[64]; ssize_t len; len = sys_read(fd, buf, 0, sizeof(buf)); - if(len < 0) + if (len < 0) panic("failed on read\n"); dprintf("read returned %Ld\n", (long long)len); } @@ -2529,8 +2518,8 @@ vfs_test(void) { struct stat stat; - err = sys_rstat("/boot/kernel", &stat); - if(err < 0) + err = sys_read_stat("/boot/kernel", &stat); + if (err < 0) panic("err stating '/boot/kernel'\n"); dprintf("stat results:\n"); dprintf("\tvnid 0x%Lx\n\ttype %d\n\tsize 0x%Lx\n", stat.st_ino, stat.st_mode, stat.st_size); @@ -2538,7 +2527,6 @@ vfs_test(void) #endif dprintf("vfs_test() done\n"); -// panic("foo\n"); return 0; } @@ -2555,11 +2543,11 @@ vfs_load_fs_module(const char *name) // sprintf(path, "/boot/addons/fs/%s", name); id = elf_load_kspace(path, ""); - if(id < 0) + if (id < 0) return id; bootstrap = (void *)elf_lookup_symbol(id, "fs_bootstrap"); - if(!bootstrap) + if (!bootstrap) return ERR_VFS_INVALID_FS; bootstrap(); @@ -2621,7 +2609,7 @@ vfs_register_filesystem(const char *name, struct fs_calls *calls) struct fs_container *container; container = (struct fs_container *)kmalloc(sizeof(struct fs_container)); - if(container == NULL) + if (container == NULL) return ENOMEM; container->name = name; @@ -2644,29 +2632,29 @@ vfs_init(kernel_args *ka) struct vnode *v; vnode_table = hash_init(VNODE_HASH_TABLE_SIZE, (addr)&v->next - (addr)v, &vnode_compare, &vnode_hash); - if(vnode_table == NULL) + if (vnode_table == NULL) panic("vfs_init: error creating vnode hash table\n"); } { struct fs_mount *mount; mounts_table = hash_init(MOUNTS_HASH_TABLE_SIZE, (addr)&mount->next - (addr)mount, &mount_compare, &mount_hash); - if(mounts_table == NULL) + if (mounts_table == NULL) panic("vfs_init: error creating mounts hash table\n"); } fs_list = NULL; root_vnode = NULL; - if(mutex_init(&vfs_mutex, "vfs_lock") < 0) + if (mutex_init(&vfs_mutex, "vfs_lock") < 0) panic("vfs_init: error allocating vfs lock\n"); - if(mutex_init(&vfs_mount_op_mutex, "vfs_mount_op_lock") < 0) + if (mutex_init(&vfs_mount_op_mutex, "vfs_mount_op_lock") < 0) panic("vfs_init: error allocating vfs_mount_op lock\n"); - if(mutex_init(&vfs_mount_mutex, "vfs_mount_lock") < 0) + if (mutex_init(&vfs_mount_mutex, "vfs_mount_lock") < 0) panic("vfs_init: error allocating vfs_mount lock\n"); - if(mutex_init(&vfs_vnode_mutex, "vfs_vnode_lock") < 0) + if (mutex_init(&vfs_vnode_mutex, "vfs_vnode_lock") < 0) panic("vfs_init: error allocating vfs_vnode lock\n"); return 0;