Loading fs/btrfs/super.c +65 −119 Original line number Diff line number Diff line Loading @@ -18,124 +18,6 @@ static struct inode_operations btrfs_dir_inode_operations; static struct super_operations btrfs_super_ops; static struct file_operations btrfs_dir_file_operations; #if 0 /* some random number */ static struct super_operations ramfs_ops; static struct backing_dev_info ramfs_backing_dev_info = { .ra_pages = 0, /* No readahead */ .capabilities = BDI_CAP_NO_ACCT_DIRTY | BDI_CAP_NO_WRITEBACK | BDI_CAP_MAP_DIRECT | BDI_CAP_MAP_COPY | BDI_CAP_READ_MAP | BDI_CAP_WRITE_MAP | BDI_CAP_EXEC_MAP, }; struct inode *ramfs_get_inode(struct super_block *sb, int mode, dev_t dev) { struct inode * inode = new_inode(sb); if (inode) { inode->i_mode = mode; inode->i_uid = current->fsuid; inode->i_gid = current->fsgid; inode->i_blocks = 0; inode->i_mapping->a_ops = &ramfs_aops; inode->i_mapping->backing_dev_info = &ramfs_backing_dev_info; inode->i_atime = inode->i_mtime = inode->i_ctime = CURRENT_TIME; switch (mode & S_IFMT) { default: init_special_inode(inode, mode, dev); break; case S_IFREG: inode->i_op = &ramfs_file_inode_operations; inode->i_fop = &ramfs_file_operations; break; case S_IFDIR: inode->i_op = &ramfs_dir_inode_operations; inode->i_fop = &simple_dir_operations; /* directory inodes start off with i_nlink == 2 (for "." entry) */ inc_nlink(inode); break; case S_IFLNK: inode->i_op = &page_symlink_inode_operations; break; } } return inode; } /* * File creation. Allocate an inode, and we're done.. */ /* SMP-safe */ static int ramfs_mknod(struct inode *dir, struct dentry *dentry, int mode, dev_t dev) { struct inode * inode = ramfs_get_inode(dir->i_sb, mode, dev); int error = -ENOSPC; if (inode) { if (dir->i_mode & S_ISGID) { inode->i_gid = dir->i_gid; if (S_ISDIR(mode)) inode->i_mode |= S_ISGID; } d_instantiate(dentry, inode); dget(dentry); /* Extra count - pin the dentry in core */ error = 0; dir->i_mtime = dir->i_ctime = CURRENT_TIME; } return error; } static int ramfs_mkdir(struct inode * dir, struct dentry * dentry, int mode) { int retval = ramfs_mknod(dir, dentry, mode | S_IFDIR, 0); if (!retval) inc_nlink(dir); return retval; } static int ramfs_create(struct inode *dir, struct dentry *dentry, int mode, struct nameidata *nd) { return ramfs_mknod(dir, dentry, mode | S_IFREG, 0); } static int ramfs_symlink(struct inode * dir, struct dentry *dentry, const char * symname) { struct inode *inode; int error = -ENOSPC; inode = ramfs_get_inode(dir->i_sb, S_IFLNK|S_IRWXUGO, 0); if (inode) { int l = strlen(symname)+1; error = page_symlink(inode, symname, l); if (!error) { if (dir->i_mode & S_ISGID) inode->i_gid = dir->i_gid; d_instantiate(dentry, inode); dget(dentry); dir->i_mtime = dir->i_ctime = CURRENT_TIME; } else iput(inode); } return error; } static struct inode_operations ramfs_dir_inode_operations = { .create = ramfs_create, .lookup = simple_lookup, .link = simple_link, .unlink = simple_unlink, .symlink = ramfs_symlink, .mkdir = ramfs_mkdir, .rmdir = simple_rmdir, .mknod = ramfs_mknod, .rename = simple_rename, }; #endif static void btrfs_read_locked_inode(struct inode *inode) { struct btrfs_path path; Loading Loading @@ -533,9 +415,11 @@ static struct inode *btrfs_new_inode(struct btrfs_trans_handle *trans, inode->i_ino = objectid; inode->i_blocks = 0; inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME_SEC; /* FIXME do this on link */ if (mode & S_IFDIR) inode->i_size = 3; fill_inode_item(&inode_item, inode); key.objectid = objectid; key.flags = 0; key.offset = 0; Loading Loading @@ -603,6 +487,67 @@ static int btrfs_create(struct inode *dir, struct dentry *dentry, return err; } static int btrfs_make_empty_dir(struct btrfs_trans_handle *trans, struct inode *inode, struct inode *dir) { struct btrfs_root *root = btrfs_sb(inode->i_sb); int ret; char buf[2]; buf[0] = '.'; buf[1] = '.'; ret = btrfs_insert_dir_item(trans, root, buf, 1, inode->i_ino, inode->i_ino, 1); if (ret) goto error; ret = btrfs_insert_dir_item(trans, root, buf, 2, inode->i_ino, dir->i_ino, 1); error: return ret; } static int btrfs_mkdir(struct inode *dir, struct dentry *dentry, int mode) { struct inode *inode; struct btrfs_trans_handle *trans; struct btrfs_root *root = btrfs_sb(dir->i_sb); int err = 0; int drop_on_err = 0; mutex_lock(&root->fs_info->fs_mutex); trans = btrfs_start_transaction(root, 1); if (IS_ERR(trans)) { err = PTR_ERR(trans); goto out_unlock; } inode = btrfs_new_inode(trans, dir, S_IFDIR | mode); if (IS_ERR(inode)) { err = PTR_ERR(inode); goto out_fail; } drop_on_err = 1; inode->i_op = &btrfs_dir_inode_operations; inode->i_fop = &btrfs_dir_file_operations; err = btrfs_make_empty_dir(trans, inode, dir); if (err) goto out_fail; err = btrfs_add_link(trans, dentry, inode); if (err) goto out_fail; d_instantiate(dentry, inode); mark_inode_dirty(inode); drop_on_err = 0; out_fail: btrfs_end_transaction(trans, root); out_unlock: mutex_unlock(&root->fs_info->fs_mutex); if (drop_on_err) iput(inode); return err; } static int btrfs_sync_fs(struct super_block *sb, int wait) { struct btrfs_trans_handle *trans; Loading Loading @@ -661,6 +606,7 @@ static struct inode_operations btrfs_dir_inode_operations = { .lookup = btrfs_lookup, .create = btrfs_create, .unlink = btrfs_unlink, .mkdir = btrfs_mkdir, }; static struct file_operations btrfs_dir_file_operations = { Loading Loading
fs/btrfs/super.c +65 −119 Original line number Diff line number Diff line Loading @@ -18,124 +18,6 @@ static struct inode_operations btrfs_dir_inode_operations; static struct super_operations btrfs_super_ops; static struct file_operations btrfs_dir_file_operations; #if 0 /* some random number */ static struct super_operations ramfs_ops; static struct backing_dev_info ramfs_backing_dev_info = { .ra_pages = 0, /* No readahead */ .capabilities = BDI_CAP_NO_ACCT_DIRTY | BDI_CAP_NO_WRITEBACK | BDI_CAP_MAP_DIRECT | BDI_CAP_MAP_COPY | BDI_CAP_READ_MAP | BDI_CAP_WRITE_MAP | BDI_CAP_EXEC_MAP, }; struct inode *ramfs_get_inode(struct super_block *sb, int mode, dev_t dev) { struct inode * inode = new_inode(sb); if (inode) { inode->i_mode = mode; inode->i_uid = current->fsuid; inode->i_gid = current->fsgid; inode->i_blocks = 0; inode->i_mapping->a_ops = &ramfs_aops; inode->i_mapping->backing_dev_info = &ramfs_backing_dev_info; inode->i_atime = inode->i_mtime = inode->i_ctime = CURRENT_TIME; switch (mode & S_IFMT) { default: init_special_inode(inode, mode, dev); break; case S_IFREG: inode->i_op = &ramfs_file_inode_operations; inode->i_fop = &ramfs_file_operations; break; case S_IFDIR: inode->i_op = &ramfs_dir_inode_operations; inode->i_fop = &simple_dir_operations; /* directory inodes start off with i_nlink == 2 (for "." entry) */ inc_nlink(inode); break; case S_IFLNK: inode->i_op = &page_symlink_inode_operations; break; } } return inode; } /* * File creation. Allocate an inode, and we're done.. */ /* SMP-safe */ static int ramfs_mknod(struct inode *dir, struct dentry *dentry, int mode, dev_t dev) { struct inode * inode = ramfs_get_inode(dir->i_sb, mode, dev); int error = -ENOSPC; if (inode) { if (dir->i_mode & S_ISGID) { inode->i_gid = dir->i_gid; if (S_ISDIR(mode)) inode->i_mode |= S_ISGID; } d_instantiate(dentry, inode); dget(dentry); /* Extra count - pin the dentry in core */ error = 0; dir->i_mtime = dir->i_ctime = CURRENT_TIME; } return error; } static int ramfs_mkdir(struct inode * dir, struct dentry * dentry, int mode) { int retval = ramfs_mknod(dir, dentry, mode | S_IFDIR, 0); if (!retval) inc_nlink(dir); return retval; } static int ramfs_create(struct inode *dir, struct dentry *dentry, int mode, struct nameidata *nd) { return ramfs_mknod(dir, dentry, mode | S_IFREG, 0); } static int ramfs_symlink(struct inode * dir, struct dentry *dentry, const char * symname) { struct inode *inode; int error = -ENOSPC; inode = ramfs_get_inode(dir->i_sb, S_IFLNK|S_IRWXUGO, 0); if (inode) { int l = strlen(symname)+1; error = page_symlink(inode, symname, l); if (!error) { if (dir->i_mode & S_ISGID) inode->i_gid = dir->i_gid; d_instantiate(dentry, inode); dget(dentry); dir->i_mtime = dir->i_ctime = CURRENT_TIME; } else iput(inode); } return error; } static struct inode_operations ramfs_dir_inode_operations = { .create = ramfs_create, .lookup = simple_lookup, .link = simple_link, .unlink = simple_unlink, .symlink = ramfs_symlink, .mkdir = ramfs_mkdir, .rmdir = simple_rmdir, .mknod = ramfs_mknod, .rename = simple_rename, }; #endif static void btrfs_read_locked_inode(struct inode *inode) { struct btrfs_path path; Loading Loading @@ -533,9 +415,11 @@ static struct inode *btrfs_new_inode(struct btrfs_trans_handle *trans, inode->i_ino = objectid; inode->i_blocks = 0; inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME_SEC; /* FIXME do this on link */ if (mode & S_IFDIR) inode->i_size = 3; fill_inode_item(&inode_item, inode); key.objectid = objectid; key.flags = 0; key.offset = 0; Loading Loading @@ -603,6 +487,67 @@ static int btrfs_create(struct inode *dir, struct dentry *dentry, return err; } static int btrfs_make_empty_dir(struct btrfs_trans_handle *trans, struct inode *inode, struct inode *dir) { struct btrfs_root *root = btrfs_sb(inode->i_sb); int ret; char buf[2]; buf[0] = '.'; buf[1] = '.'; ret = btrfs_insert_dir_item(trans, root, buf, 1, inode->i_ino, inode->i_ino, 1); if (ret) goto error; ret = btrfs_insert_dir_item(trans, root, buf, 2, inode->i_ino, dir->i_ino, 1); error: return ret; } static int btrfs_mkdir(struct inode *dir, struct dentry *dentry, int mode) { struct inode *inode; struct btrfs_trans_handle *trans; struct btrfs_root *root = btrfs_sb(dir->i_sb); int err = 0; int drop_on_err = 0; mutex_lock(&root->fs_info->fs_mutex); trans = btrfs_start_transaction(root, 1); if (IS_ERR(trans)) { err = PTR_ERR(trans); goto out_unlock; } inode = btrfs_new_inode(trans, dir, S_IFDIR | mode); if (IS_ERR(inode)) { err = PTR_ERR(inode); goto out_fail; } drop_on_err = 1; inode->i_op = &btrfs_dir_inode_operations; inode->i_fop = &btrfs_dir_file_operations; err = btrfs_make_empty_dir(trans, inode, dir); if (err) goto out_fail; err = btrfs_add_link(trans, dentry, inode); if (err) goto out_fail; d_instantiate(dentry, inode); mark_inode_dirty(inode); drop_on_err = 0; out_fail: btrfs_end_transaction(trans, root); out_unlock: mutex_unlock(&root->fs_info->fs_mutex); if (drop_on_err) iput(inode); return err; } static int btrfs_sync_fs(struct super_block *sb, int wait) { struct btrfs_trans_handle *trans; Loading Loading @@ -661,6 +606,7 @@ static struct inode_operations btrfs_dir_inode_operations = { .lookup = btrfs_lookup, .create = btrfs_create, .unlink = btrfs_unlink, .mkdir = btrfs_mkdir, }; static struct file_operations btrfs_dir_file_operations = { Loading