Почему мой метод readdir для моей файловой системы возвращает неверные размеры для каталогов? - PullRequest
0 голосов
/ 05 октября 2018

Это проблема с домашним заданием из курса по операционным системам, я должен исправить методы create и readdir для простой файловой системы.Я исправил метод create (файлы правильно сообщают размер с помощью ls -als), но каталог сообщает размер моей структуры inode *, однако в нем содержится много файлов.Хотя это нормально, я чувствую, что могу быть более точным.Я думаю, что хочу следовать указателям в блоках данных моего каталога, а затем суммировать i_sizes дочерних файлов, но что, если я хочу вложить каталоги?Я бы очень признателен за некоторые советы о том, как подойти к этому,

Мой метод Readdir:

static int
#if LINUX_VERSION_CODE < KERNEL_VERSION(3,10,0)
vvsfs_readdir(struct file *filp, void *dirent, filldir_t filldir)
#else
vvsfs_readdir(struct file *filp, struct dir_context *ctx)
#endif
{
    struct inode *i;
    struct vvsfs_inode dirdata;
    int num_dirs;
    struct vvsfs_dir_entry *dent;
    int error, k;

    if (DEBUG) printk("vvsfs - readdir\n");

#if LINUX_VERSION_CODE < KERNEL_VERSION(3,10,0)
    i = filp->f_dentry->d_inode;
#else
    i = file_inode(filp);
#endif
    vvsfs_readblock(i->i_sb, i->i_ino, &dirdata);
    num_dirs = dirdata.size / sizeof(struct vvsfs_dir_entry);

    if (DEBUG) printk("Number of entries %d fpos %Ld\n", num_dirs, filp->f_pos);

    error = 0;
    k=0;
    dent = (struct vvsfs_dir_entry *) &dirdata.data;
    while (!error && filp->f_pos < dirdata.size && k < num_dirs) 
    {
        printk("adding name : %s ino : %d\n",dent->name, dent->inode_number);
#if LINUX_VERSION_CODE < KERNEL_VERSION(3,10,0)
        error = filldir(dirent, 
            dent->name, strlen(dent->name), filp->f_pos, dent->inode_number,DT_REG);
        if (error)
            break;
        filp->f_pos += sizeof(struct vvsfs_dir_entry);

#else
        if (dent->inode_number) 
        {
            if (!dir_emit (ctx, dent->name, strnlen (dent->name, MAXNAME),
                dent->inode_number, DT_UNKNOWN)) return 0;
        }
        ctx->pos += sizeof(struct vvsfs_dir_entry);
#endif
        k++;
        dent++;
    }
    // update_atime(i);
    // Sizes updated here
    i->i_size = dirdata.size;   
    printk("inode size is now %d", i->i_size);
    mark_inode_dirty(i);


    printk("done readdir\n");

    return 0;
}

Моя простая структура inode

struct vvsfs_inode
{
    int is_empty;
    int is_directory;
    int size;
    char data[MAXFILESIZE];
};
...