Better permission handling, add chmod/chown

This commit is contained in:
Mark
2020-01-14 14:07:57 +02:00
parent b47a465770
commit 94aee57638
10 changed files with 123 additions and 27 deletions
+3
View File
@@ -22,3 +22,6 @@ int sys_access(const char *path, int mode);
// TODO: const struct termios *termp, const struct winsize *winp
int sys_openpty(int *master, int *slave);
int sys_chmod(const char *path, mode_t mode);
int sys_chown(const char *path, uid_t uid, gid_t gid);
+2
View File
@@ -45,6 +45,8 @@ struct vnode_operations {
int (*stat) (struct vnode *at, struct stat *st);
int (*access) (struct vnode *node, uid_t *uid, gid_t *gid, mode_t *mode);
int (*chmod) (struct vnode *node, mode_t mode);
int (*chown) (struct vnode *node, uid_t uid, gid_t gid);
int (*readlink) (struct vnode *at, char *buf, size_t lim);
+2
View File
@@ -39,6 +39,8 @@ int vfs_readdir(struct vfs_ioctx *ctx, struct ofile *fd, struct dirent *ent);
int vfs_unlink(struct vfs_ioctx *ctx, const char *path);
int vfs_rmdir(struct vfs_ioctx *ctx, const char *path);
int vfs_mkdir(struct vfs_ioctx *ctx, const char *path, mode_t mode);
int vfs_chmod(struct vfs_ioctx *ctx, const char *path, mode_t mode);
int vfs_chown(struct vfs_ioctx *ctx, const char *path, uid_t uid, gid_t gid);
int vfs_access(struct vfs_ioctx *ctx, const char *path, int accmode);
int vfs_stat(struct vfs_ioctx *ctx, const char *path, struct stat *st);
+2
View File
@@ -13,6 +13,8 @@
#define SYSCALL_NR_CREAT 85
#define SYSCALL_NR_UNLINK 87
#define SYSCALL_NR_READDIR 89
#define SYSCALL_NR_CHMOD 90
#define SYSCALL_NR_CHOWN 92
#define SYSCALL_NR_BRK 12
#define SYSCALL_NR_NANOSLEEP 35
+15
View File
@@ -185,3 +185,18 @@ int sys_openpty(int *master, int *slave) {
return -EINVAL;
}
int sys_chmod(const char *path, mode_t mode) {
struct thread *thr = get_cpu()->thread;
_assert(thr);
_assert(path);
return vfs_chmod(&thr->ioctx, path, mode);
}
int sys_chown(const char *path, uid_t uid, gid_t gid) {
struct thread *thr = get_cpu()->thread;
_assert(thr);
_assert(path);
return vfs_chown(&thr->ioctx, path, uid, gid);
}
+2
View File
@@ -26,6 +26,8 @@ const void *amd64_syscall_jmp_table[256] = {
[SYSCALL_NR_MKDIR] = sys_mkdir,
[SYSCALL_NR_CREAT] = sys_creat,
[SYSCALL_NR_RMDIR] = sys_rmdir,
[SYSCALL_NR_CHMOD] = sys_chmod,
[SYSCALL_NR_CHOWN] = sys_chown,
// Process
[SYSCALL_NR_EXIT] = sys_exit,
+1
View File
@@ -74,6 +74,7 @@ static ssize_t tty_read(struct chrdev *tty, void *buf, size_t pos, size_t lim) {
memcpy((char *) buf + p, ibuf, rd);
rem -= rd;
p += rd;
}
return p;
+26 -27
View File
@@ -30,8 +30,8 @@ static int ext2_vnode_truncate(struct vnode *vn, size_t length);
static ssize_t ext2_vnode_readdir(struct ofile *fd, struct dirent *ent);
//static void ext2_vnode_destroy(vnode_t *vn);
static int ext2_vnode_stat(struct vnode *vn, struct stat *st);
//static int ext2_vnode_chmod(vnode_t *vn, mode_t mode);
//static int ext2_vnode_chown(vnode_t *vn, uid_t uid, gid_t gid);
static int ext2_vnode_chmod(struct vnode *vn, mode_t mode);
static int ext2_vnode_chown(struct vnode *vn, uid_t uid, gid_t gid);
static int ext2_vnode_unlink(struct vnode *vn);
//static int ext2_vnode_access(vnode_t *vn, uid_t *uid, gid_t *gid, mode_t *mode);
static int ext2_vnode_readlink(struct vnode *vn, char *dst, size_t lim);
@@ -48,8 +48,8 @@ struct vnode_operations ext2_vnode_ops = {
.readlink = ext2_vnode_readlink,
// .symlink = ext2_vnode_symlink,
//
// .chmod = ext2_vnode_chmod,
// .chown = ext2_vnode_chown,
.chmod = ext2_vnode_chmod,
.chown = ext2_vnode_chown,
.stat = ext2_vnode_stat,
.unlink = ext2_vnode_unlink,
// .access = ext2_vnode_access,
@@ -427,7 +427,6 @@ static ssize_t ext2_vnode_write(struct ofile *fd, const void *buf, size_t count)
}
}
kinfo("Wrote %u bytes\n", written);
return written;
}
@@ -585,28 +584,28 @@ static int ext2_vnode_stat(struct vnode *vn, struct stat *st) {
return 0;
}
//static int ext2_vnode_chmod(vnode_t *vn, mode_t mode) {
// _assert(vn && vn->fs && vn->fs_data);
// struct ext2_inode *inode = (struct ext2_inode *) vn->fs_data;
//
// // Update only access mode
// inode->type_perm &= ~0x1FF;
// inode->type_perm |= mode & 0x1FF;
//
// // Write the inode back
// return ext2_write_inode(vn->fs, inode, vn->fs_number);
//}
//
//static int ext2_vnode_chown(vnode_t *vn, uid_t uid, gid_t gid) {
// _assert(vn && vn->fs && vn->fs_data);
// struct ext2_inode *inode = (struct ext2_inode *) vn->fs_data;
//
// inode->gid = gid;
// inode->uid = uid;
//
// // Write the inode back
// return ext2_write_inode(vn->fs, inode, vn->fs_number);
//}
static int ext2_vnode_chmod(struct vnode *vn, mode_t mode) {
_assert(vn && vn->fs && vn->fs_data);
struct ext2_inode *inode = (struct ext2_inode *) vn->fs_data;
// Update only access mode
inode->type_perm &= ~0x1FF;
inode->type_perm |= mode & 0x1FF;
// Write the inode back
return ext2_write_inode(vn->fs, inode, vn->ino);
}
static int ext2_vnode_chown(struct vnode *vn, uid_t uid, gid_t gid) {
_assert(vn && vn->fs && vn->fs_data);
struct ext2_inode *inode = (struct ext2_inode *) vn->fs_data;
inode->gid = gid;
inode->uid = uid;
// Write the inode back
return ext2_write_inode(vn->fs, inode, vn->ino);
}
static int ext2_vnode_unlink(struct vnode *node) {
_assert(node);
+13
View File
@@ -28,12 +28,17 @@ static int tarfs_vnode_open(struct ofile *of, int opt);
static int tarfs_vnode_stat(struct vnode *node, struct stat *st);
static ssize_t tarfs_vnode_read(struct ofile *fd, void *buf, size_t count);
static off_t tarfs_vnode_lseek(struct ofile *fd, off_t off, int whence);
// Nodes can be chmod/chown'd
static int tarfs_vnode_chmod(struct vnode *node, mode_t mode);
static int tarfs_vnode_chown(struct vnode *node, uid_t uid, gid_t gid);
static struct vnode_operations _tarfs_vnode_op = {
.stat = tarfs_vnode_stat,
.read = tarfs_vnode_read,
.open = tarfs_vnode_open,
.lseek = tarfs_vnode_lseek,
.chmod = tarfs_vnode_chmod,
.chown = tarfs_vnode_chown,
};
static ssize_t tarfs_octal(const char *buf, size_t lim) {
@@ -313,6 +318,14 @@ static off_t tarfs_vnode_lseek(struct ofile *fd, off_t offset, int whence) {
return fd->pos;
}
static int tarfs_vnode_chmod(struct vnode *node, mode_t mode) {
return 0;
}
static int tarfs_vnode_chown(struct vnode *node, uid_t uid, gid_t gid) {
return 0;
}
//
void tarfs_init(void) {
+57
View File
@@ -545,3 +545,60 @@ off_t vfs_lseek(struct vfs_ioctx *ctx, struct ofile *fd, off_t offset, int whenc
return node->op->lseek(fd, offset, whence);
}
int vfs_chmod(struct vfs_ioctx *ctx, const char *path, mode_t mode) {
_assert(ctx);
_assert(path);
struct vnode *node;
int res;
mode &= 0x1FF;
if ((res = vfs_find(ctx, ctx->cwd_vnode, path, &node)) != 0) {
return res;
}
// Only root or file owner can do that
if (ctx->uid != 0 && ctx->uid != node->uid) {
return -EACCES;
}
if (!node->op || !node->op->chmod) {
return -EINVAL;
}
if ((res = node->op->chmod(node, mode)) != 0) {
return res;
}
node->mode = mode;
return 0;
}
int vfs_chown(struct vfs_ioctx *ctx, const char *path, uid_t uid, gid_t gid) {
struct vnode *node;
int res;
if ((res = vfs_find(ctx, ctx->cwd_vnode, path, &node)) != 0) {
return res;
}
// Only root can chown
if (ctx->uid != 0) {
return -EACCES;
}
if (!node->op || !node->op->chown) {
return -EINVAL;
}
if ((res = node->op->chown(node, uid, gid)) != 0) {
return res;
}
node->uid = uid;
node->gid = gid;
return 0;
}