diff options
Diffstat (limited to 'fs/btrfs/inode.c')
-rw-r--r-- | fs/btrfs/inode.c | 135 |
1 files changed, 2 insertions, 133 deletions
diff --git a/fs/btrfs/inode.c b/fs/btrfs/inode.c index adb169d739ce..48a3dc030807 100644 --- a/fs/btrfs/inode.c +++ b/fs/btrfs/inode.c | |||
@@ -2073,104 +2073,6 @@ err: | |||
2073 | return ret; | 2073 | return ret; |
2074 | } | 2074 | } |
2075 | 2075 | ||
2076 | /* Kernels earlier than 2.6.28 still have the NFS deadlock where nfsd | ||
2077 | will call the file system's ->lookup() method from within its | ||
2078 | filldir callback, which in turn was called from the file system's | ||
2079 | ->readdir() method. And will deadlock for many file systems. */ | ||
2080 | #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,28) | ||
2081 | |||
2082 | struct nfshack_dirent { | ||
2083 | u64 ino; | ||
2084 | loff_t offset; | ||
2085 | int namlen; | ||
2086 | unsigned int d_type; | ||
2087 | char name[]; | ||
2088 | }; | ||
2089 | |||
2090 | struct nfshack_readdir { | ||
2091 | char *dirent; | ||
2092 | size_t used; | ||
2093 | int full; | ||
2094 | }; | ||
2095 | |||
2096 | |||
2097 | |||
2098 | static int btrfs_nfshack_filldir(void *__buf, const char *name, int namlen, | ||
2099 | loff_t offset, u64 ino, unsigned int d_type) | ||
2100 | { | ||
2101 | struct nfshack_readdir *buf = __buf; | ||
2102 | struct nfshack_dirent *de = (void *)(buf->dirent + buf->used); | ||
2103 | unsigned int reclen; | ||
2104 | |||
2105 | reclen = ALIGN(sizeof(struct nfshack_dirent) + namlen, sizeof(u64)); | ||
2106 | if (buf->used + reclen > PAGE_SIZE) { | ||
2107 | buf->full = 1; | ||
2108 | return -EINVAL; | ||
2109 | } | ||
2110 | |||
2111 | de->namlen = namlen; | ||
2112 | de->offset = offset; | ||
2113 | de->ino = ino; | ||
2114 | de->d_type = d_type; | ||
2115 | memcpy(de->name, name, namlen); | ||
2116 | buf->used += reclen; | ||
2117 | |||
2118 | return 0; | ||
2119 | } | ||
2120 | |||
2121 | static int btrfs_nfshack_readdir(struct file *file, void *dirent, | ||
2122 | filldir_t filldir) | ||
2123 | { | ||
2124 | struct nfshack_readdir buf; | ||
2125 | struct nfshack_dirent *de; | ||
2126 | int err; | ||
2127 | int size; | ||
2128 | loff_t offset; | ||
2129 | |||
2130 | buf.dirent = (void *)__get_free_page(GFP_KERNEL); | ||
2131 | if (!buf.dirent) | ||
2132 | return -ENOMEM; | ||
2133 | |||
2134 | offset = file->f_pos; | ||
2135 | |||
2136 | do { | ||
2137 | unsigned int reclen; | ||
2138 | |||
2139 | buf.used = 0; | ||
2140 | buf.full = 0; | ||
2141 | err = btrfs_real_readdir(file, &buf, btrfs_nfshack_filldir); | ||
2142 | if (err) | ||
2143 | break; | ||
2144 | |||
2145 | size = buf.used; | ||
2146 | |||
2147 | if (!size) | ||
2148 | break; | ||
2149 | |||
2150 | de = (struct nfshack_dirent *)buf.dirent; | ||
2151 | while (size > 0) { | ||
2152 | offset = de->offset; | ||
2153 | |||
2154 | if (filldir(dirent, de->name, de->namlen, de->offset, | ||
2155 | de->ino, de->d_type)) | ||
2156 | goto done; | ||
2157 | offset = file->f_pos; | ||
2158 | |||
2159 | reclen = ALIGN(sizeof(*de) + de->namlen, | ||
2160 | sizeof(u64)); | ||
2161 | size -= reclen; | ||
2162 | de = (struct nfshack_dirent *)((char *)de + reclen); | ||
2163 | } | ||
2164 | } while (buf.full); | ||
2165 | |||
2166 | done: | ||
2167 | free_page((unsigned long)buf.dirent); | ||
2168 | file->f_pos = offset; | ||
2169 | |||
2170 | return err; | ||
2171 | } | ||
2172 | #endif | ||
2173 | |||
2174 | int btrfs_write_inode(struct inode *inode, int wait) | 2076 | int btrfs_write_inode(struct inode *inode, int wait) |
2175 | { | 2077 | { |
2176 | struct btrfs_root *root = BTRFS_I(inode)->root; | 2078 | struct btrfs_root *root = BTRFS_I(inode)->root; |
@@ -3311,13 +3213,8 @@ unsigned long btrfs_force_ra(struct address_space *mapping, | |||
3311 | { | 3213 | { |
3312 | pgoff_t req_size = last_index - offset + 1; | 3214 | pgoff_t req_size = last_index - offset + 1; |
3313 | 3215 | ||
3314 | #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,23) | ||
3315 | offset = page_cache_readahead(mapping, ra, file, offset, req_size); | ||
3316 | return offset; | ||
3317 | #else | ||
3318 | page_cache_sync_readahead(mapping, ra, file, offset, req_size); | 3216 | page_cache_sync_readahead(mapping, ra, file, offset, req_size); |
3319 | return offset + req_size; | 3217 | return offset + req_size; |
3320 | #endif | ||
3321 | } | 3218 | } |
3322 | 3219 | ||
3323 | struct inode *btrfs_alloc_inode(struct super_block *sb) | 3220 | struct inode *btrfs_alloc_inode(struct super_block *sb) |
@@ -3373,14 +3270,7 @@ void btrfs_destroy_inode(struct inode *inode) | |||
3373 | kmem_cache_free(btrfs_inode_cachep, BTRFS_I(inode)); | 3270 | kmem_cache_free(btrfs_inode_cachep, BTRFS_I(inode)); |
3374 | } | 3271 | } |
3375 | 3272 | ||
3376 | #if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26) | ||
3377 | static void init_once(void *foo) | 3273 | static void init_once(void *foo) |
3378 | #elif LINUX_VERSION_CODE > KERNEL_VERSION(2,6,23) | ||
3379 | static void init_once(struct kmem_cache * cachep, void *foo) | ||
3380 | #else | ||
3381 | static void init_once(void * foo, struct kmem_cache * cachep, | ||
3382 | unsigned long flags) | ||
3383 | #endif | ||
3384 | { | 3274 | { |
3385 | struct btrfs_inode *ei = (struct btrfs_inode *) foo; | 3275 | struct btrfs_inode *ei = (struct btrfs_inode *) foo; |
3386 | 3276 | ||
@@ -3403,22 +3293,10 @@ void btrfs_destroy_cachep(void) | |||
3403 | 3293 | ||
3404 | struct kmem_cache *btrfs_cache_create(const char *name, size_t size, | 3294 | struct kmem_cache *btrfs_cache_create(const char *name, size_t size, |
3405 | unsigned long extra_flags, | 3295 | unsigned long extra_flags, |
3406 | #if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26) | 3296 | void (*ctor)(void *)) |
3407 | void (*ctor)(void *) | ||
3408 | #elif LINUX_VERSION_CODE > KERNEL_VERSION(2,6,23) | ||
3409 | void (*ctor)(struct kmem_cache *, void *) | ||
3410 | #else | ||
3411 | void (*ctor)(void *, struct kmem_cache *, | ||
3412 | unsigned long) | ||
3413 | #endif | ||
3414 | ) | ||
3415 | { | 3297 | { |
3416 | return kmem_cache_create(name, size, 0, (SLAB_RECLAIM_ACCOUNT | | 3298 | return kmem_cache_create(name, size, 0, (SLAB_RECLAIM_ACCOUNT | |
3417 | SLAB_MEM_SPREAD | extra_flags), ctor | 3299 | SLAB_MEM_SPREAD | extra_flags), ctor); |
3418 | #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,23) | ||
3419 | ,NULL | ||
3420 | #endif | ||
3421 | ); | ||
3422 | } | 3300 | } |
3423 | 3301 | ||
3424 | int btrfs_init_cachep(void) | 3302 | int btrfs_init_cachep(void) |
@@ -3666,12 +3544,7 @@ static int btrfs_set_page_dirty(struct page *page) | |||
3666 | return __set_page_dirty_nobuffers(page); | 3544 | return __set_page_dirty_nobuffers(page); |
3667 | } | 3545 | } |
3668 | 3546 | ||
3669 | #if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,26) | ||
3670 | static int btrfs_permission(struct inode *inode, int mask) | 3547 | static int btrfs_permission(struct inode *inode, int mask) |
3671 | #else | ||
3672 | static int btrfs_permission(struct inode *inode, int mask, | ||
3673 | struct nameidata *nd) | ||
3674 | #endif | ||
3675 | { | 3548 | { |
3676 | if (btrfs_test_flag(inode, READONLY) && (mask & MAY_WRITE)) | 3549 | if (btrfs_test_flag(inode, READONLY) && (mask & MAY_WRITE)) |
3677 | return -EACCES; | 3550 | return -EACCES; |
@@ -3702,11 +3575,7 @@ static struct inode_operations btrfs_dir_ro_inode_operations = { | |||
3702 | static struct file_operations btrfs_dir_file_operations = { | 3575 | static struct file_operations btrfs_dir_file_operations = { |
3703 | .llseek = generic_file_llseek, | 3576 | .llseek = generic_file_llseek, |
3704 | .read = generic_read_dir, | 3577 | .read = generic_read_dir, |
3705 | #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,28) | ||
3706 | .readdir = btrfs_nfshack_readdir, | ||
3707 | #else /* NFSd readdir/lookup deadlock is fixed */ | ||
3708 | .readdir = btrfs_real_readdir, | 3578 | .readdir = btrfs_real_readdir, |
3709 | #endif | ||
3710 | .unlocked_ioctl = btrfs_ioctl, | 3579 | .unlocked_ioctl = btrfs_ioctl, |
3711 | #ifdef CONFIG_COMPAT | 3580 | #ifdef CONFIG_COMPAT |
3712 | .compat_ioctl = btrfs_ioctl, | 3581 | .compat_ioctl = btrfs_ioctl, |