new: devfs删除文件夹

This commit is contained in:
fslongjin 2022-09-12 23:56:31 +08:00
parent d60f1a8f80
commit 9f2b080cda
24 changed files with 366 additions and 92 deletions

View File

@ -132,7 +132,11 @@
"limits.h": "c",
"block.h": "c",
"blk_types.h": "c",
"mutex.h": "c"
"mutex.h": "c",
"mount.h": "c",
"internal.h": "c",
"devfs.h": "c",
"devfs-types.h": "c"
},
"C_Cpp.errorSquiggles": "Enabled",
"esbonio.sphinx.confDir": ""

View File

@ -173,11 +173,11 @@ struct vfs_index_node_t
  inode的属性。可选值如下
> - VFS_ATTR_FILE
> - VFS_IF_FILE
>
> - VFS_ATTR_DIR
> - VFS_IF_DIR
>
> - VFS_ATTR_DEVICE
> - VFS_IF_DEVICE
**sb**

View File

@ -48,11 +48,11 @@
文件夹类型:
``#define VFS_ATTR_FILE (1UL << 0)``
``#define VFS_IF_FILE (1UL << 0)``
``#define VFS_ATTR_DIR (1UL << 1)``
``#define VFS_IF_DIR (1UL << 1)``
``#define VFS_ATTR_DEVICE (1UL << 2)``
``#define VFS_IF_DEVICE (1UL << 2)``
缓冲区长度的默认值

View File

@ -4,6 +4,18 @@
#pragma GCC push_options
#pragma GCC optimize("O0")
/**
* @brief condition为true时bug
*
*/
#define BUG_ON(condition) ({ \
int __ret_bug_on = !!(condition); \
if (unlikely(__ret_bug_on)) \
kBUG("BUG at %s:%d", __FILE__, __LINE__); \
unlikely(__ret_bug_on); \
})
/**
* @brief condition为true时输出警告信息
*

View File

@ -1,6 +1,8 @@
#include "VFS.h"
#include "mount.h"
#include "internal.h"
#include <common/kprint.h>
#include <debug/bug.h>
#include <common/dirent.h>
#include <common/string.h>
#include <common/errno.h>
@ -46,7 +48,9 @@ struct vfs_superblock_t *vfs_mount_fs(const char *path, char *name, struct block
{
struct vfs_superblock_t *sb = p->read_superblock(blk);
if (strcmp(path, "/") == 0) // 如果挂载到的是'/'挂载点,则让其成为最顶层的文件系统
{
vfs_root_sb = sb;
}
else
{
kdebug("to mount %s", name);
@ -168,7 +172,7 @@ struct vfs_dir_entry_t *vfs_path_walk(const char *path, uint64_t flags)
// 如果没有找到dentry缓存则申请新的dentry
if (dentry == NULL)
{
dentry = vfs_alloc_dentry(tmp_path_len+1);
dentry = vfs_alloc_dentry(tmp_path_len + 1);
memcpy(dentry->name, (void *)tmp_path, tmp_path_len);
dentry->name[tmp_path_len] = '\0';
@ -236,13 +240,13 @@ int vfs_fill_dirent(void *buf, ino_t d_ino, char *name, int namelen, unsigned ch
/**
* @brief
*
*
* @param path
* @param mode
* @param from_userland
* @param from_userland
* @return int64_t
*/
int64_t vfs_mkdir(const char* path, mode_t mode, bool from_userland)
int64_t vfs_mkdir(const char *path, mode_t mode, bool from_userland)
{
uint32_t pathlen;
if (from_userland)
@ -267,10 +271,9 @@ int64_t vfs_mkdir(const char* path, mode_t mode, bool from_userland)
// 路径格式不合法(必须使用绝对路径)
if (last_slash < 0)
return ENOTDIR;
return -ENOTDIR;
char *buf = (char *)kmalloc(last_slash + 1, 0);
memset(buf, 0, pathlen + 1);
char *buf = (char *)kzalloc(last_slash + 2, 0);
// 拷贝字符串(不包含要被创建的部分)
if (from_userland)
@ -341,13 +344,12 @@ uint64_t sys_mkdir(struct pt_regs *regs)
return vfs_mkdir(path, mode, true);
else
return vfs_mkdir(path, mode, false);
}
/**
* @brief
*
* @param filename
*
* @param filename
* @param flags
* @return uint64_t
*/
@ -445,23 +447,23 @@ uint64_t do_open(const char *filename, int flags)
return -ENOENT;
// 要求打开文件夹而目标不是文件夹
if ((flags & O_DIRECTORY) && (dentry->dir_inode->attribute != VFS_ATTR_DIR))
if ((flags & O_DIRECTORY) && (dentry->dir_inode->attribute != VFS_IF_DIR))
return -ENOTDIR;
// // 要找的目标是文件夹
// if ((flags & O_DIRECTORY) && dentry->dir_inode->attribute == VFS_ATTR_DIR)
// if ((flags & O_DIRECTORY) && dentry->dir_inode->attribute == VFS_IF_DIR)
// return -EISDIR;
// // todo: 引入devfs后删除这段代码
// // 暂时遇到设备文件的话就将其first clus设置为特定值
// if (path_len >= 5 && filename[0] == '/' && filename[1] == 'd' && filename[2] == 'e' && filename[3] == 'v' && filename[4] == '/')
// {
// if (dentry->dir_inode->attribute & VFS_ATTR_FILE)
// if (dentry->dir_inode->attribute & VFS_IF_FILE)
// {
// // 对于fat32文件系统上面的设备文件设置其起始扇区
// ((struct fat32_inode_info_t *)(dentry->dir_inode->private_inode_info))->first_clus |= 0xf0000000;
// dentry->dir_inode->sb->sb_ops->write_inode(dentry->dir_inode);
// dentry->dir_inode->attribute |= VFS_ATTR_DEVICE;
// dentry->dir_inode->attribute |= VFS_IF_DEVICE;
// }
// }
@ -544,6 +546,122 @@ struct vfs_dir_entry_t *vfs_alloc_dentry(const int name_size)
return dentry;
}
/**
* @brief dentry
*
* 1dentry
* 2dentry的inode拥有写
* 3dentry指向的是文件夹isdir为false
* 3dentry指向的是文件isdir为true
* @param dentry dentry
* @param isdir
* @return int
*/
int vfs_may_delete(struct vfs_dir_entry_t *dentry, bool isdir)
{
// 当dentry没有inode的时候认为是bug
BUG_ON(dentry->dir_inode == NULL);
// todo: 进行权限检查
if (isdir) // 要删除文件夹
{
if (!D_ISDIR(dentry))
return -ENOTDIR;
else if (IS_ROOT(dentry))
return -EBUSY;
}
else if (D_ISDIR(dentry)) // 要删除文件但是当前是文件夹
return -EISDIR;
return 0;
}
/**
* @brief
*
* @param path
* @param from_userland
* @return int64_t
*/
int64_t vfs_rmdir(const char *path, bool from_userland)
{
uint32_t pathlen;
if (from_userland)
pathlen = strnlen_user(path, PAGE_4K_SIZE - 1);
else
pathlen = strnlen(path, PAGE_4K_SIZE - 1);
if (pathlen == 0)
return -ENOENT;
int last_slash = -1;
// 去除末尾的'/'
for (int i = pathlen - 1; i >= 0; --i)
{
if (path[i] != '/')
{
last_slash = i + 1;
break;
}
}
// 路径格式不合法
if (last_slash < 0)
return -ENOTDIR;
else if (path[0] != '/')
return -EINVAL;
char *buf = (char *)kzalloc(last_slash + 2, 0);
// 拷贝字符串(不包含要被创建的部分)
if (from_userland)
strncpy_from_user(buf, path, last_slash);
else
strncpy(buf, path, last_slash);
buf[last_slash + 1] = '\0';
struct vfs_dir_entry_t *dentry = vfs_path_walk(buf, 0);
if (dentry == NULL)
return -ENOENT;
int retval = vfs_may_delete(dentry, true);
if (retval != 0)
return retval;
// todo: 对dentry和inode加锁
retval = -EBUSY;
if (is_local_mountpoint(dentry))
goto out;
// todo:
retval = dentry->dir_inode->inode_ops->rmdir(dentry->dir_inode, dentry);
if (retval != 0)
goto out;
dentry->dir_inode->attribute |= VFS_IF_DEAD; // 将当前inode标记为dead
dont_mount(dentry); // 将当前dentry标记为不可被挂载
detach_mounts(dentry); // 清理同样挂载在该路径的所有挂载点的挂载树
vfs_dentry_put(dentry); // 释放dentry
out:;
// todo: 对dentry和inode放锁
return retval;
}
/**
* @brief
*
* @param r8
* @return uint64_t
*/
uint64_t sys_rmdir(struct pt_regs *regs)
{
if (SYSCALL_FROM_USER(regs))
return vfs_rmdir((char *)regs->r8, true);
else
return vfs_rmdir((char *)regs->r8, false);
}
/**
* @brief vfs
*

View File

@ -28,12 +28,13 @@ extern struct vfs_superblock_t *vfs_root_sb;
#define VFS_MAX_PATHLEN 1024
/**
* @brief
* @brief inode的属
*
*/
#define VFS_ATTR_FILE (1UL << 0)
#define VFS_ATTR_DIR (1UL << 1)
#define VFS_ATTR_DEVICE (1UL << 2)
#define VFS_IF_FILE (1UL << 0)
#define VFS_IF_DIR (1UL << 1)
#define VFS_IF_DEVICE (1UL << 2)
#define VFS_IF_DEAD (1UL<<3) /* removed, but still open directory */
struct vfs_super_block_operations_t;
struct vfs_inode_operations_t;
@ -41,10 +42,13 @@ struct vfs_inode_operations_t;
struct vfs_index_node_t;
struct vfs_dir_entry_operations_t;
#define VFS_DF_MOUNTED (1 << 0) // 当前dentry是一个挂载点
#define VFS_DF_CANNOT_MOUNT (1 << 1) // 当前dentry是一个挂载点
struct vfs_dir_entry_t
{
char *name;
int name_length;
uint32_t d_flags; // dentry标志位
struct List child_node_list;
struct List subdirs_list;
@ -218,8 +222,8 @@ struct vfs_dir_entry_t *vfs_alloc_dentry(const int name_size);
/**
* @brief
*
* @param filename
*
* @param filename
* @param flags
* @return uint64_t
*/
@ -227,10 +231,19 @@ uint64_t do_open(const char *filename, int flags);
/**
* @brief
*
*
* @param path
* @param mode
* @param from_userland
* @param from_userland
* @return int64_t
*/
int64_t vfs_mkdir(const char* path, mode_t mode, bool from_userland);
int64_t vfs_mkdir(const char *path, mode_t mode, bool from_userland);
/**
* @brief
*
* @param path
* @param from_userland
* @return int64_t
*/
int64_t vfs_rmdir(const char *path, bool from_userland);

View File

@ -0,0 +1,19 @@
#include "internal.h"
/**
* @brief dentry
*
* @param dentry dentry
*/
void vfs_dentry_put(struct vfs_dir_entry_t * dentry)
{
// todo: 加锁、放锁
list_del(&dentry->child_node_list);// 从父dentry中删除
// todo: 清除子目录的dentry
dentry->dir_ops->release(dentry);
kfree(dentry);
}

View File

@ -0,0 +1,41 @@
#pragma once
#include "VFS.h"
#include "mount.h"
/**
* @brief dentry
*
* 1dentry
* 2dentry拥有写
* 3dentry指向的是文件夹isdir为false
* 3dentry指向的是文件isdir为true
* @param dentry dentry
* @param isdir
* @return int
*/
int vfs_may_delete(struct vfs_dir_entry_t *dentry, bool isdir);
#define D_ISDIR(dentry) ((dentry)->dir_inode->attribute & VFS_IF_DIR)
// 判断是否为根目录
#define IS_ROOT(x) ((x) == (x)->parent)
/**
* @brief dentry是否为挂载点
*
* @param dentry
*/
static inline bool is_local_mountpoint(struct vfs_dir_entry_t *dentry)
{
if (D_MOUNTED(dentry))
return true;
else
return false;
}
/**
* @brief dentry
*
* @param dentry dentry
*/
void vfs_dentry_put(struct vfs_dir_entry_t * dentry);

View File

@ -29,16 +29,17 @@ int do_mount(struct vfs_dir_entry_t *old_dentry, struct vfs_dir_entry_t *new_den
list_init(&mp->mnt_list);
mp->dentry = old_dentry;
mp->parent_dentry = old_dentry->parent;
// kdebug("&new_dentry->name=%#018lx, &old_dentry->name=%#018lx", &new_dentry->name, &old_dentry->name);
// 拷贝名称
strncpy(new_dentry->name, old_dentry->name, old_dentry->name_length);
new_dentry->d_flags |= VFS_DF_MOUNTED; // 标记新的dentry是一个挂载点
list_init(&new_dentry->child_node_list);
list_init(&new_dentry->subdirs_list);
new_dentry->parent = old_dentry->parent;
// 将新的dentry的list结点替换掉父dentry的列表中的old_dentry的list结点
list_replace(&old_dentry->child_node_list, &new_dentry->child_node_list);
@ -50,11 +51,11 @@ int do_mount(struct vfs_dir_entry_t *old_dentry, struct vfs_dir_entry_t *new_den
/**
* @brief
*
*
* @param dentry dentry
* @return int
*/
int do_umount(struct vfs_dir_entry_t* dentry)
int do_umount(struct vfs_dir_entry_t *dentry)
{
// todo: 实现umount主要是结点的恢复问题

View File

@ -1,6 +1,6 @@
#pragma once
#include <common/glib.h>
#include "VFS.h"
/**
* @brief (dentry被挂载其他文件系统之后)
*
@ -30,8 +30,31 @@ int do_mount(struct vfs_dir_entry_t *old_dentry, struct vfs_dir_entry_t *new_den
/**
* @brief
*
*
* @param dentry dentry
* @return int
*/
int do_umount(struct vfs_dir_entry_t* dentry);
int do_umount(struct vfs_dir_entry_t *dentry);
// 判断dentry是否是一个挂载点
#define D_MOUNTED(x) ((x)->d_flags & VFS_DF_MOUNTED)
/**
* @brief dentry标记为
*
* @param dentry dentry
*/
static inline void dont_mount(struct vfs_dir_entry_t *dentry)
{
// todo: 对dentry加锁
dentry->d_flags |= VFS_DF_CANNOT_MOUNT;
}
static inline void detach_mounts(struct vfs_dir_entry_t *dentry)
{
if (!D_MOUNTED(dentry))
return; // 如果当前文件夹不是一个挂载点,则直接返回
// todo:如果当前文件夹是一个挂载点则对同样挂载在当前文件夹下的dentry进行清理。以免造成内存泄露
// 可参考 linux5.17或以上的detach_mounts()函数
}

View File

@ -55,7 +55,7 @@ int __devfs_chardev_register(struct devfs_private_inode_info_t *private_info, st
struct vfs_dir_entry_t *dentry = vfs_alloc_dentry(namelen + 1);
__devfs_fill_dentry(dentry, devname);
__devfs_fill_inode(dentry, __devfs_alloc_inode(), VFS_ATTR_DEVICE, private_info);
__devfs_fill_inode(dentry, __devfs_alloc_inode(), VFS_IF_DEVICE, private_info);
// 将dentry挂载到char文件夹下
__devfs_dentry_bind_parent(chardev_folder_dentry, dentry);

View File

@ -33,11 +33,11 @@ struct vfs_superblock_t *devfs_read_superblock(struct block_device *blk)
return &devfs_sb;
}
static void devfs_write_superblock(struct vfs_superblock_t *sb) {}
static void devfs_write_superblock(struct vfs_superblock_t *sb) {return 0; }
static void devfs_put_superblock(struct vfs_superblock_t *sb) {}
static void devfs_put_superblock(struct vfs_superblock_t *sb) {return 0; }
static void devfs_write_inode(struct vfs_index_node_t *inode) {}
static void devfs_write_inode(struct vfs_index_node_t *inode) {return 0; }
struct vfs_super_block_operations_t devfs_sb_ops =
{
.write_superblock = &devfs_write_superblock,
@ -45,13 +45,13 @@ struct vfs_super_block_operations_t devfs_sb_ops =
.write_inode = &devfs_write_inode,
};
static long devfs_compare(struct vfs_dir_entry_t *parent_dEntry, char *source_filename, char *dest_filename) {}
static long devfs_compare(struct vfs_dir_entry_t *parent_dEntry, char *source_filename, char *dest_filename) {return 0; }
static long devfs_hash(struct vfs_dir_entry_t *dEntry, char *filename) {}
static long devfs_hash(struct vfs_dir_entry_t *dEntry, char *filename) {return 0; }
static long devfs_release(struct vfs_dir_entry_t *dEntry) {}
static long devfs_release(struct vfs_dir_entry_t *dEntry) { return 0; }
static long devfs_iput(struct vfs_dir_entry_t *dEntry, struct vfs_index_node_t *inode) {}
static long devfs_iput(struct vfs_dir_entry_t *dEntry, struct vfs_index_node_t *inode) {return 0; }
struct vfs_dir_entry_operations_t devfs_dentry_ops =
{
@ -65,10 +65,10 @@ static long devfs_open(struct vfs_index_node_t *inode, struct vfs_file_t *file_p
{
return 0;
}
static long devfs_close(struct vfs_index_node_t *inode, struct vfs_file_t *file_ptr) {}
static long devfs_read(struct vfs_file_t *file_ptr, char *buf, int64_t count, long *position) {}
static long devfs_write(struct vfs_file_t *file_ptr, char *buf, int64_t count, long *position) {}
static long devfs_lseek(struct vfs_file_t *file_ptr, long offset, long origin) {}
static long devfs_close(struct vfs_index_node_t *inode, struct vfs_file_t *file_ptr) {return 0; }
static long devfs_read(struct vfs_file_t *file_ptr, char *buf, int64_t count, long *position) {return 0; }
static long devfs_write(struct vfs_file_t *file_ptr, char *buf, int64_t count, long *position) {return 0; }
static long devfs_lseek(struct vfs_file_t *file_ptr, long offset, long origin) {return 0; }
static long devfs_ioctl(struct vfs_index_node_t *inode, struct vfs_file_t *file_ptr, uint64_t cmd, uint64_t arg) { return 0; }
static long devfs_readdir(struct vfs_file_t *file_ptr, void *dirent, vfs_filldir_t filler)
@ -94,10 +94,10 @@ static long devfs_readdir(struct vfs_file_t *file_ptr, void *dirent, vfs_filldir
char *name = (char *)kzalloc(target_dent->name_length + 1, 0);
strncpy(name, target_dent->name, target_dent->name_length);
uint32_t dentry_type;
if (target_dent->dir_inode->attribute & VFS_ATTR_DIR)
dentry_type = VFS_ATTR_DIR;
if (target_dent->dir_inode->attribute & VFS_IF_DIR)
dentry_type = VFS_IF_DIR;
else
dentry_type = VFS_ATTR_DEVICE;
dentry_type = VFS_IF_DEVICE;
return filler(dirent, file_ptr->position - 1, name, target_dent->name_length, dentry_type, file_ptr->position - 1);
failed:;
@ -123,6 +123,7 @@ struct vfs_file_operations_t devfs_file_ops =
*/
static long devfs_create(struct vfs_index_node_t *parent_inode, struct vfs_dir_entry_t *dest_dEntry, int mode)
{
return 0;
}
static struct vfs_dir_entry_t *devfs_lookup(struct vfs_index_node_t *parent_inode, struct vfs_dir_entry_t *dest_dEntry)
@ -148,18 +149,18 @@ static long devfs_mkdir(struct vfs_index_node_t *inode, struct vfs_dir_entry_t *
dEntry->dir_inode = (struct vfs_index_node_t *)kzalloc(sizeof(struct vfs_index_node_t), 0);
dEntry->dir_inode->file_ops = &devfs_file_ops;
dEntry->dir_inode->inode_ops = &devfs_inode_ops;
dEntry->dir_ops = &devfs_dentry_ops;
// todo: 增加private inode info
dEntry->dir_inode->private_inode_info = NULL;
dEntry->dir_inode->sb = &devfs_sb;
dEntry->dir_inode->attribute = VFS_ATTR_DIR;
dEntry->dir_inode->attribute = VFS_IF_DIR;
return 0;
}
static long devfs_rmdir(struct vfs_index_node_t *inode, struct vfs_dir_entry_t *dEntry) {}
static long devfs_rename(struct vfs_index_node_t *old_inode, struct vfs_dir_entry_t *old_dEntry, struct vfs_index_node_t *new_inode, struct vfs_dir_entry_t *new_dEntry) {}
static long devfs_getAttr(struct vfs_dir_entry_t *dEntry, uint64_t *attr) {}
static long devfs_setAttr(struct vfs_dir_entry_t *dEntry, uint64_t *attr) {}
static long devfs_rmdir(struct vfs_index_node_t *inode, struct vfs_dir_entry_t *dEntry) { return 0; }
static long devfs_rename(struct vfs_index_node_t *old_inode, struct vfs_dir_entry_t *old_dEntry, struct vfs_index_node_t *new_inode, struct vfs_dir_entry_t *new_dEntry) {return 0; }
static long devfs_getAttr(struct vfs_dir_entry_t *dEntry, uint64_t *attr) {return 0; }
static long devfs_setAttr(struct vfs_dir_entry_t *dEntry, uint64_t *attr) {return 0; }
struct vfs_inode_operations_t devfs_inode_ops = {
.create = &devfs_create,
.lookup = &devfs_lookup,
@ -187,7 +188,7 @@ static __always_inline void __devfs_init_root_inode()
// todo: 增加private inode info
devfs_root_dentry->dir_inode->private_inode_info = NULL;
devfs_root_dentry->dir_inode->sb = &devfs_sb;
devfs_root_dentry->dir_inode->attribute = VFS_ATTR_DIR;
devfs_root_dentry->dir_inode->attribute = VFS_IF_DIR;
}
/**
* @brief devfs的根dentry
@ -251,7 +252,6 @@ void devfs_init()
vfs_register_filesystem(&devfs_fs_type);
vfs_mount_fs(__devfs_mount_path, "DEVFS", NULL);
__devfs_chardev_init();
// todo: 当rootfs实现后将ps/2键盘的注册改为在驱动程序中进行目前没有rootfs因此还不能在不依赖fat32的情况下挂载设备

View File

@ -58,7 +58,7 @@ static inline struct vfs_dir_entry_t *__devfs_find_dentry(struct vfs_dir_entry_t
static inline struct vfs_dir_entry_t *__devfs_find_dir(struct vfs_dir_entry_t *parent_dentry, const char *name)
{
struct vfs_dir_entry_t *target_dent = __devfs_find_dentry(parent_dentry, name);
if (target_dent->dir_inode->attribute & VFS_ATTR_DIR) // 名称相符且为目录则返回dentry
if (target_dent->dir_inode->attribute & VFS_IF_DIR) // 名称相符且为目录则返回dentry
return target_dent;
else
return NULL; // 否则直接返回空

View File

@ -293,7 +293,7 @@ find_lookup_success:; // 找到目标dentry
p->file_size = tmp_dEntry->DIR_FileSize;
// 计算文件占用的扇区数, 由于最小存储单位是簇,因此需要按照簇的大小来对齐扇区
p->blocks = (p->file_size + fsbi->bytes_per_clus - 1) / fsbi->bytes_per_sec;
p->attribute = (tmp_dEntry->DIR_Attr & ATTR_DIRECTORY) ? VFS_ATTR_DIR : VFS_ATTR_FILE;
p->attribute = (tmp_dEntry->DIR_Attr & ATTR_DIRECTORY) ? VFS_IF_DIR : VFS_IF_FILE;
p->sb = parent_inode->sb;
p->file_ops = &fat32_file_ops;
p->inode_ops = &fat32_inode_ops;
@ -315,8 +315,8 @@ find_lookup_success:; // 找到目标dentry
// 暂时使用fat32的高4bit来标志设备文件
// todo: 引入devfs后删除这段代码
if ((tmp_dEntry->DIR_FstClusHI >> 12) && (p->attribute & VFS_ATTR_FILE))
p->attribute |= VFS_ATTR_DEVICE;
if ((tmp_dEntry->DIR_FstClusHI >> 12) && (p->attribute & VFS_IF_FILE))
p->attribute |= VFS_IF_DEVICE;
dest_dentry->dir_inode = p;
dest_dentry->dir_ops = &fat32_dEntry_ops;
@ -394,7 +394,7 @@ struct vfs_superblock_t *fat32_read_superblock(struct block_device *blk)
sb_ptr->root->dir_inode->file_size = 0;
// 计算文件占用的扇区数, 由于最小存储单位是簇,因此需要按照簇的大小来对齐扇区
sb_ptr->root->dir_inode->blocks = (sb_ptr->root->dir_inode->file_size + fsbi->bytes_per_clus - 1) / fsbi->bytes_per_sec;
sb_ptr->root->dir_inode->attribute = VFS_ATTR_DIR;
sb_ptr->root->dir_inode->attribute = VFS_IF_DIR;
sb_ptr->root->dir_inode->sb = sb_ptr; // 反向绑定对应的超级块
// 初始化inode信息
@ -826,7 +826,7 @@ long fat32_create(struct vfs_index_node_t *parent_inode, struct vfs_dir_entry_t
struct fat32_inode_info_t *finode = (struct fat32_inode_info_t *)kmalloc(sizeof(struct fat32_inode_info_t), 0);
memset((void *)finode, 0, sizeof(struct fat32_inode_info_t));
inode->attribute = VFS_ATTR_FILE;
inode->attribute = VFS_IF_FILE;
inode->file_ops = &fat32_file_ops;
inode->file_size = 0;
inode->sb = parent_inode->sb;
@ -933,7 +933,7 @@ int64_t fat32_mkdir(struct vfs_index_node_t *parent_inode, struct vfs_dir_entry_
// ====== 初始化inode =======
struct vfs_index_node_t *inode = (struct vfs_index_node_t *)kmalloc(sizeof(struct vfs_index_node_t), 0);
memset(inode, 0, sizeof(struct vfs_index_node_t));
inode->attribute = VFS_ATTR_DIR;
inode->attribute = VFS_IF_DIR;
inode->blocks = fsbi->sec_per_clus;
inode->file_ops = &fat32_file_ops;
inode->file_size = 0;
@ -1230,9 +1230,9 @@ find_dir_success:;
file_ptr->position += 32;
// todo: 计算ino_t
if (dentry_type & ATTR_DIRECTORY)
dentry_type = VFS_ATTR_DIR;
dentry_type = VFS_IF_DIR;
else
dentry_type = VFS_ATTR_FILE;
dentry_type = VFS_IF_FILE;
return filler(dirent, 0, dir_name, name_len, dentry_type, 0);
}

View File

@ -335,7 +335,7 @@ void fat32_fill_shortname(struct vfs_dir_entry_t *dEntry, struct fat32_Directory
target->DIR_Name[tmp_index] = 0x20;
++tmp_index;
}
if (dEntry->dir_inode->attribute & VFS_ATTR_DIR)
if (dEntry->dir_inode->attribute & VFS_IF_DIR)
{
while (tmp_index < 11)
{
@ -355,7 +355,7 @@ void fat32_fill_shortname(struct vfs_dir_entry_t *dEntry, struct fat32_Directory
struct vfs_index_node_t *inode = dEntry->dir_inode;
target->DIR_Attr = 0;
if (inode->attribute & VFS_ATTR_DIR)
if (inode->attribute & VFS_IF_DIR)
target->DIR_Attr |= ATTR_DIRECTORY;
target->DIR_FileSize = dEntry->dir_inode->file_size;

View File

@ -154,7 +154,7 @@ struct vfs_file_t *process_open_exec_file(char *path)
if (dentry == NULL)
return (void *)-ENOENT;
if (dentry->dir_inode->attribute == VFS_ATTR_DIR)
if (dentry->dir_inode->attribute == VFS_IF_DIR)
return (void *)-ENOTDIR;
filp = (struct vfs_file_t *)kmalloc(sizeof(struct vfs_file_t), 0);

View File

@ -19,6 +19,7 @@ extern void syscall_int(void);
extern uint64_t sys_clock(struct pt_regs *regs);
extern uint64_t sys_mstat(struct pt_regs *regs);
extern uint64_t sys_open(struct pt_regs *regs);
extern uint64_t sys_rmdir(struct pt_regs *regs);
/**
* @brief
@ -415,7 +416,7 @@ uint64_t sys_chdir(struct pt_regs *regs)
return -ENOENT;
// kdebug("dentry->name=%s, namelen=%d", dentry->name, dentry->name_length);
// 目标不是目录
if (dentry->dir_inode->attribute != VFS_ATTR_DIR)
if (dentry->dir_inode->attribute != VFS_IF_DIR)
return -ENOTDIR;
return 0;
@ -602,5 +603,6 @@ system_call_t system_call_table[MAX_SYSTEM_CALL_NUM] =
[19] = sys_clock,
[20] = sys_pipe,
[21] = sys_mstat,
[22 ... 254] = system_call_not_exists,
[22] = sys_rmdir,
[23 ... 254] = system_call_not_exists,
[255] = sys_ahci_end_req};

View File

@ -15,6 +15,11 @@ extern void ret_from_system_call(void); // 导出从系统调用返回的函数
extern system_call_t system_call_table[MAX_SYSTEM_CALL_NUM];
// 判断系统调用是否来自用户态
#define SYSCALL_FROM_USER(regs) ((regs)->cs & USER_CS)
// 判断系统调用是否来自内核态
#define SYSCALL_FROM_KERNEL(regs) (!SYSCALL_FROM_USER(regs))
/**
* @brief
*

View File

@ -33,6 +33,7 @@
#define SYS_PIPE 20
#define SYS_MSTAT 21 // 获取系统的内存状态信息
#define SYS_RMDIR 22 // 删除文件夹
#define SYS_AHCI_END_REQ 255 // AHCI DMA请求结束end_request的系统调用

View File

@ -210,7 +210,7 @@ int shell_cmd_cd(int argc, char **argv)
new_path[current_dir_len] = '/';
strcat(new_path, argv[1] + dest_offset);
int x = chdir(new_path);
if (x == 0) // 成功切换目录
{
free(shell_current_path);
@ -257,12 +257,12 @@ int shell_cmd_ls(int argc, char **argv)
break;
int color = COLOR_WHITE;
if (buf->d_type & VFS_ATTR_DIR)
if (buf->d_type & VFS_IF_DIR)
color = COLOR_YELLOW;
else if (buf->d_type & VFS_ATTR_FILE)
else if (buf->d_type & VFS_IF_FILE)
color = COLOR_INDIGO;
else if(buf->d_type & VFS_ATTR_DEVICE)
color= COLOR_GREEN;
else if (buf->d_type & VFS_IF_DEVICE)
color = COLOR_GREEN;
char output_buf[256] = {0};
@ -405,7 +405,21 @@ int shell_cmd_mkdir(int argc, char **argv)
* @return int
*/
// todo:
int shell_cmd_rmdir(int argc, char **argv) {}
int shell_cmd_rmdir(int argc, char **argv)
{
const char *full_path = NULL;
int result_path_len = -1;
if (argv[1][0] == '/')
full_path = argv[1];
else
full_path = get_target_filepath(argv[1], &result_path_len);
int retval = rmdir(full_path);
printf("rmdir: path=%s, retval=%d", full_path, retval);
if (argv != NULL)
free(argv);
return retval;
}
/**
* @brief
@ -483,7 +497,7 @@ int shell_cmd_free(int argc, char **argv)
struct mstat_t mst = {0};
retval = mstat(&mst);
if(retval!=0)
if (retval != 0)
{
printf("Failed: retval=%d", retval);
goto done;
@ -491,15 +505,15 @@ int shell_cmd_free(int argc, char **argv)
printf("\ttotal\tused\tfree\tshared\tcache\tavailable\n");
printf("Mem:\t");
if(argc==1) // 按照kb显示
if (argc == 1) // 按照kb显示
{
printf("%ld\t%ld\t%ld\t%ld\t%ld\t%ld\t\n", mst.total>>10,mst.used>>10,mst.free>>10, mst.shared>>10, mst.cache_used>>10, mst.available>>10);
printf("%ld\t%ld\t%ld\t%ld\t%ld\t%ld\t\n", mst.total >> 10, mst.used >> 10, mst.free >> 10, mst.shared >> 10, mst.cache_used >> 10, mst.available >> 10);
}
else // 按照MB显示
else // 按照MB显示
{
printf("%ld\t%ld\t%ld\t%ld\t%ld\t%ld\t\n", mst.total>>20,mst.used>>20,mst.free>>20, mst.shared>>20, mst.cache_used>>20, mst.available>>20);
printf("%ld\t%ld\t%ld\t%ld\t%ld\t%ld\t\n", mst.total >> 20, mst.used >> 20, mst.free >> 20, mst.shared >> 20, mst.cache_used >> 20, mst.available >> 20);
}
done:;
if (argv != NULL)
free(argv);

View File

@ -3,12 +3,12 @@
/**
* @brief copy from vfs.h
* @brief inode的属copy from vfs.h
*
*/
#define VFS_ATTR_FILE (1UL << 0)
#define VFS_ATTR_DIR (1UL << 1)
#define VFS_ATTR_DEVICE (1UL << 2)
#define VFS_IF_FILE (1UL << 0)
#define VFS_IF_DIR (1UL << 1)
#define VFS_IF_DEVICE (1UL << 2)
#define DIR_BUF_SIZE 256
/**

View File

@ -142,7 +142,19 @@ int execv(const char *path, char *const argv[])
return -1;
}
int retval = syscall_invoke(SYS_EXECVE, (uint64_t)path, (uint64_t)argv, 0, 0, 0, 0, 0, 0);
if(retval != 0)
if (retval != 0)
return -1;
else return 0;
else
return 0;
}
/**
* @brief
*
* @param path
* @return int
*/
int rmdir(const char *path)
{
return syscall_invoke(SYS_RMDIR, (uint64_t)path, 0, 0, 0, 0, 0, 0, 0);
}

View File

@ -97,3 +97,11 @@ int execv(const char* path, char * const argv[]);
* @return int
*/
extern int usleep(useconds_t usec);
/**
* @brief
*
* @param path
* @return int
*/
int rmdir(const char* path);

View File

@ -27,6 +27,7 @@
#define SYS_PIPE 20
#define SYS_MSTAT 21 // 获取系统的内存状态信息
#define SYS_RMDIR 22 // 删除文件夹
/**
* @brief