faccessat and fstatat

This commit is contained in:
Mark
2020-07-26 23:02:13 +03:00
parent 26df7ce9aa
commit 040b94499c
11 changed files with 109 additions and 130 deletions
+8 -4
View File
@@ -45,14 +45,18 @@ void *syscall_table[256] = {
//SUPERSEDED BY:
[SYSCALL_NR_OPENAT] = sys_openat,
[SYSCALL_NR_CLOSE] = sys_close,
[SYSCALL_NR_STAT] = sys_stat,
[SYSCALL_NR_FSTAT] = sys_fstat,
[SYSCALL_NR_LSTAT] = sys_lstat,
//[SYSCALL_NR_STAT] = sys_stat,
//[SYSCALL_NR_FSTAT] = sys_fstat,
//[SYSCALL_NR_LSTAT] = sys_lstat,
//SUPERSEDED BY:
[SYSCALL_NR_FSTATAT] = sys_fstatat,
[SYSCALL_NR_LSEEK] = sys_lseek,
[SYSCALL_NR_MMAP] = sys_mmap,
[SYSCALL_NR_MUNMAP] = sys_munmap,
[SYSCALL_NR_IOCTL] = sys_ioctl,
[SYSCALL_NR_ACCESS] = sys_access,
//[SYSCALL_NR_ACCESS] = sys_access,
//SUPERSEDED BY:
[SYSCALL_NR_FACCESSAT] = sys_faccessat,
[SYSCALL_NR_PIPE] = sys_pipe,
[SYSCALL_NR_SELECT] = sys_select,
[SYSCALL_NR_DUP] = sys_dup,
+26 -50
View File
@@ -508,76 +508,52 @@ void vfs_close(struct vfs_ioctx *ctx, struct ofile *fd) {
}
}
int vfs_access(struct vfs_ioctx *ctx, const char *path, int accmode) {
struct vnode *node;
int res;
int vfs_faccessat(struct vfs_ioctx *ctx, struct vnode *at, const char *path, int mode, int flags) {
_assert(ctx);
_assert(path);
if ((res = vfs_find(ctx, ctx->cwd_vnode, path, 0, &node)) != 0) {
struct vnode *node;
int res;
if ((res = vfs_find(ctx, at, path, flags & AT_SYMLINK_NOFOLLOW, &node)) != 0) {
return res;
}
if (accmode == F_OK) {
// Just test that file exists
if (mode == F_OK) {
return 0;
}
return vfs_access_node(ctx, node, accmode);
return vfs_access_node(ctx, node, mode);
}
int vfs_fstat(struct vfs_ioctx *ctx, struct ofile *fd, struct stat *st) {
int res;
_assert(ctx);
_assert(fd);
_assert(!(fd->flags & OF_SOCKET));
_assert(st);
struct vnode *node = fd->file.vnode;
_assert(node);
if (!node->op || !node->op->stat) {
return -EINVAL;
}
return node->op->stat(node, st);
}
int vfs_lstat(struct vfs_ioctx *ctx, const char *path, struct stat *st) {
int vfs_fstatat(struct vfs_ioctx *ctx, struct vnode *at, const char *path, struct stat *st, int flags) {
struct vnode *node;
int res;
_assert(ctx);
_assert(path);
_assert(st);
if ((res = vfs_find(ctx, ctx->cwd_vnode, path, 1, &node)) != 0) {
return res;
}
if (!node->op || !node->op->stat) {
return -EINVAL;
}
return node->op->stat(node, st);
}
int vfs_stat(struct vfs_ioctx *ctx, const char *path, struct stat *st) {
struct vnode *node;
int res;
_assert(ctx);
_assert(path);
_assert(st);
if ((res = vfs_find(ctx, ctx->cwd_vnode, path, 0, &node)) != 0) {
return res;
if (!at) {
at = ctx->cwd_vnode;
}
kdebug("FSTATAT %s, %s\n", (at ? at->name : "NULL"), path);
if (flags & AT_EMPTY_PATH) {
node = at;
if (!node) {
panic("TODO: implement this (use root)\n");
}
} else {
_assert(path);
if ((res = vfs_find(ctx, at, path, flags & AT_SYMLINK_NOFOLLOW, &node)) != 0) {
return res;
}
}
if (!node->op || !node->op->stat) {
kerror("stat() not implemented for node\n");
return -EINVAL;
}
+6 -4
View File
@@ -56,10 +56,12 @@ 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_ioctl(struct vfs_ioctx *ctx, struct ofile *fd, unsigned int cmd, void *arg);
int vfs_access(struct vfs_ioctx *ctx, const char *path, int accmode);
int vfs_fstat(struct vfs_ioctx *ctx, struct ofile *fd, struct stat *st);
int vfs_lstat(struct vfs_ioctx *ctx, const char *path, struct stat *st);
int vfs_stat(struct vfs_ioctx *ctx, const char *path, struct stat *st);
//int vfs_access(struct vfs_ioctx *ctx, const char *path, int accmode);
int vfs_faccessat(struct vfs_ioctx *ctx, struct vnode *at, const char *path, int accmode, int flags);
//int vfs_fstat(struct vfs_ioctx *ctx, struct ofile *fd, struct stat *st);
//int vfs_lstat(struct vfs_ioctx *ctx, const char *path, struct stat *st);
//int vfs_stat(struct vfs_ioctx *ctx, const char *path, struct stat *st);
int vfs_fstatat(struct vfs_ioctx *ctx, struct vnode *at, const char *path, struct stat *st, int flags);
int vfs_access_check(struct vfs_ioctx *ctx, int desm, mode_t mode, uid_t uid, gid_t gid);
int vfs_access_node(struct vfs_ioctx *ctx, struct vnode *vn, int mode);
+8 -4
View File
@@ -17,10 +17,14 @@ int sys_getcwd(char *buf, size_t lim);
// REMOVED: int sys_open(const char *filename, int flags, int mode);
int sys_openat(int dfd, const char *filename, int flags, int mode);
void sys_close(int fd);
int sys_stat(const char *filename, struct stat *st);
int sys_fstat(int fd, struct stat *st);
int sys_lstat(const char *filename, struct stat *st);
int sys_access(const char *path, int mode);
//int sys_stat(const char *filename, struct stat *st);
//int sys_fstat(int fd, struct stat *st);
//int sys_lstat(const char *filename, struct stat *st);
//SUPERSEDED BY:
int sys_fstatat(int dfd, const char *pathname, struct stat *st, int flags);
//int sys_access(const char *path, int mode);
//SUPERSEDED BY:
int sys_faccessat(int dfd, const char *pathname, int mode, int flags);
int sys_pipe(int *filedes);
int sys_select(int n, fd_set *inp, fd_set *outp, fd_set *excp, struct timeval *tv);
int sys_dup(int from);
+1 -17
View File
@@ -1,11 +1,10 @@
#pragma once
#include <stdint.h>
#include "user/types.h"
#ifndef NULL
#define NULL ((void *) 0)
#endif
#if defined(__KERNEL__)
struct tm {
int tm_sec;
int tm_min;
@@ -17,18 +16,3 @@ struct tm {
int tm_yday;
int tm_isdst;
};
typedef uint32_t uid_t;
typedef uint32_t gid_t;
#endif
typedef uint64_t uintptr_t;
typedef int64_t intptr_t;
typedef uintptr_t size_t;
typedef intptr_t ssize_t;
typedef int64_t off_t;
typedef uint32_t mode_t;
typedef int32_t pid_t;
+3 -1
View File
@@ -9,7 +9,9 @@
#define X_OK 1
#define F_OK 0
#define AT_FDCWD (-100)
#define AT_FDCWD (-100)
#define AT_SYMLINK_NOFOLLOW (1 << 0)
#define AT_EMPTY_PATH (1 << 1)
// O_EXEC is a special one for opening a node for
// execution
+8 -4
View File
@@ -6,15 +6,19 @@
// SUPERSEDED BY:
#define SYSCALL_NR_OPENAT 2
#define SYSCALL_NR_CLOSE 3
#define SYSCALL_NR_STAT 4
#define SYSCALL_NR_FSTAT 5
#define SYSCALL_NR_LSTAT 6
//#define SYSCALL_NR_STAT 4
//#define SYSCALL_NR_FSTAT 5
//#define SYSCALL_NR_LSTAT 6
//SUPERSEDED BY:
#define SYSCALL_NR_FSTATAT 4
#define SYSCALL_NR_LSEEK 8
#define SYSCALL_NR_MMAP 9
#define SYSCALL_NR_MUNMAP 11
#define SYSCALL_NRX_SBRK 12
#define SYSCALL_NR_IOCTL 16
#define SYSCALL_NR_ACCESS 21
//#define SYSCALL_NR_ACCESS 21
//SUPERSEDED BY:
#define SYSCALL_NR_FACCESSAT 21
#define SYSCALL_NR_PIPE 22
#define SYSCALL_NR_SELECT 23
#define SYSCALL_NR_DUP 32
+8 -11
View File
@@ -1,24 +1,21 @@
#pragma once
#if defined(__KERNEL__)
#include <stdint.h>
#else
#include <stdint-gcc.h>
#if !defined(NULL)
#define NULL ((void *) 0)
#endif
typedef int sig_atomic_t;
typedef int32_t pid_t;
typedef int pid_t;
typedef int64_t ssize_t;
typedef uint64_t size_t;
typedef int64_t off_t;
typedef int mode_t;
typedef uint32_t mode_t;
typedef uint16_t uid_t;
typedef uint16_t gid_t;
typedef uint32_t uid_t;
typedef uint32_t gid_t;
typedef uint64_t clock_t;
typedef uint64_t useconds_t;
typedef int32_t pid_t;
+1 -1
View File
@@ -133,7 +133,7 @@ int sys_execve(const char *path, const char **argv, const char **envp) {
int res;
int was_kernel = 0;
if ((res = vfs_stat(&proc->ioctx, path, &st)) != 0) {
if ((res = vfs_fstatat(&proc->ioctx, NULL, path, &st, 0)) != 0) {
kerror("execve(%s): %s\n", path, kstrerror(res));
return res;
}
+1 -1
View File
@@ -191,7 +191,7 @@ static int elf_mod_load(struct module *mod, struct vfs_ioctx *ctx, struct ofile
int res = 0;
// Load the whole module image into memory
if ((res = vfs_fstat(ctx, fd, &st)) != 0) {
if ((res = vfs_fstatat(ctx, fd->file.vnode, NULL, &st, AT_EMPTY_PATH)) != 0) {
return res;
}
+39 -33
View File
@@ -26,6 +26,23 @@ static inline struct vfs_ioctx *get_ioctx(void) {
return &thread_self->proc->ioctx;
}
static inline int get_at_vnode(int dfd, struct vnode **at, int flags) {
if (dfd == AT_FDCWD) {
*at = get_ioctx()->cwd_vnode;
return 0;
} else {
struct ofile *fd = get_fd(dfd);
if (!fd) {
return -EBADF;
}
if (!(flags & AT_EMPTY_PATH) && !(fd->flags & OF_DIRECTORY)) {
return -ENOTDIR;
}
*at = fd->file.vnode;
return 0;
}
}
ssize_t sys_read(int fd, void *data, size_t lim) {
userptr_check(data);
struct ofile *of;
@@ -121,14 +138,8 @@ int sys_openat(int dfd, const char *filename, int flags, int mode) {
int fd = -1;
int res;
if (dfd == AT_FDCWD) {
at = get_ioctx()->cwd_vnode;
} else {
struct ofile *of = get_fd(dfd);
if (of == NULL || !(of->flags & OF_DIRECTORY)) {
return -EBADF;
}
at = of->file.vnode;
if ((res = get_at_vnode(dfd, &at, 0)) != 0) {
return res;
}
// XXX: This should be atomic
@@ -170,38 +181,33 @@ void sys_close(int fd) {
proc->fds[fd] = NULL;
}
int sys_stat(const char *filename, struct stat *st) {
userptr_check(filename);
_assert(filename);
_assert(st);
int sys_fstatat(int dfd, const char *pathname, struct stat *st, int flags) {
if (!(flags & AT_EMPTY_PATH)) {
userptr_check(pathname);
}
userptr_check(st);
return vfs_stat(get_ioctx(), filename, st);
}
struct vnode *at;
int res;
int sys_lstat(const char *filename, struct stat *st) {
userptr_check(filename);
_assert(filename);
_assert(st);
return vfs_lstat(get_ioctx(), filename, st);
}
int sys_fstat(int fd, struct stat *st) {
struct ofile *of;
_assert(st);
if (!(of = get_fd(fd))) {
return -EBADF;
if ((res = get_at_vnode(dfd, &at, flags)) != 0) {
return res;
}
return vfs_fstat(get_ioctx(), of, st);
return vfs_fstatat(get_ioctx(), at, pathname, st, flags);
}
int sys_access(const char *path, int mode) {
userptr_check(path);
_assert(path);
int sys_faccessat(int dfd, const char *pathname, int mode, int flags) {
userptr_check(pathname);
return vfs_access(get_ioctx(), path, mode);
struct vnode *at;
int res;
if ((res = get_at_vnode(dfd, &at, flags)) != 0) {
return res;
}
return vfs_faccessat(get_ioctx(), at, pathname, mode, flags);
}
int sys_pipe(int *filedes) {