aboutsummaryrefslogtreecommitdiffstats
path: root/fs/nilfs2/inode.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/nilfs2/inode.c')
-rw-r--r--fs/nilfs2/inode.c93
1 files changed, 67 insertions, 26 deletions
diff --git a/fs/nilfs2/inode.c b/fs/nilfs2/inode.c
index 0957b58f909d..eccb2f2e2315 100644
--- a/fs/nilfs2/inode.c
+++ b/fs/nilfs2/inode.c
@@ -27,6 +27,7 @@
27#include <linux/writeback.h> 27#include <linux/writeback.h>
28#include <linux/uio.h> 28#include <linux/uio.h>
29#include "nilfs.h" 29#include "nilfs.h"
30#include "btnode.h"
30#include "segment.h" 31#include "segment.h"
31#include "page.h" 32#include "page.h"
32#include "mdt.h" 33#include "mdt.h"
@@ -197,11 +198,15 @@ static int nilfs_write_begin(struct file *file, struct address_space *mapping,
197 if (unlikely(err)) 198 if (unlikely(err))
198 return err; 199 return err;
199 200
200 *pagep = NULL; 201 err = block_write_begin(mapping, pos, len, flags, pagep,
201 err = block_write_begin(file, mapping, pos, len, flags, pagep, 202 nilfs_get_block);
202 fsdata, nilfs_get_block); 203 if (unlikely(err)) {
203 if (unlikely(err)) 204 loff_t isize = mapping->host->i_size;
205 if (pos + len > isize)
206 vmtruncate(mapping->host, isize);
207
204 nilfs_transaction_abort(inode->i_sb); 208 nilfs_transaction_abort(inode->i_sb);
209 }
205 return err; 210 return err;
206} 211}
207 212
@@ -237,6 +242,19 @@ nilfs_direct_IO(int rw, struct kiocb *iocb, const struct iovec *iov,
237 /* Needs synchronization with the cleaner */ 242 /* Needs synchronization with the cleaner */
238 size = blockdev_direct_IO(rw, iocb, inode, inode->i_sb->s_bdev, iov, 243 size = blockdev_direct_IO(rw, iocb, inode, inode->i_sb->s_bdev, iov,
239 offset, nr_segs, nilfs_get_block, NULL); 244 offset, nr_segs, nilfs_get_block, NULL);
245
246 /*
247 * In case of error extending write may have instantiated a few
248 * blocks outside i_size. Trim these off again.
249 */
250 if (unlikely((rw & WRITE) && size < 0)) {
251 loff_t isize = i_size_read(inode);
252 loff_t end = offset + iov_length(iov, nr_segs);
253
254 if (end > isize)
255 vmtruncate(inode, isize);
256 }
257
240 return size; 258 return size;
241} 259}
242 260
@@ -280,16 +298,7 @@ struct inode *nilfs_new_inode(struct inode *dir, int mode)
280 /* reference count of i_bh inherits from nilfs_mdt_read_block() */ 298 /* reference count of i_bh inherits from nilfs_mdt_read_block() */
281 299
282 atomic_inc(&sbi->s_inodes_count); 300 atomic_inc(&sbi->s_inodes_count);
283 301 inode_init_owner(inode, dir, mode);
284 inode->i_uid = current_fsuid();
285 if (dir->i_mode & S_ISGID) {
286 inode->i_gid = dir->i_gid;
287 if (S_ISDIR(mode))
288 mode |= S_ISGID;
289 } else
290 inode->i_gid = current_fsgid();
291
292 inode->i_mode = mode;
293 inode->i_ino = ino; 302 inode->i_ino = ino;
294 inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME; 303 inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME;
295 304
@@ -346,7 +355,6 @@ void nilfs_free_inode(struct inode *inode)
346 struct super_block *sb = inode->i_sb; 355 struct super_block *sb = inode->i_sb;
347 struct nilfs_sb_info *sbi = NILFS_SB(sb); 356 struct nilfs_sb_info *sbi = NILFS_SB(sb);
348 357
349 clear_inode(inode);
350 /* XXX: check error code? Is there any thing I can do? */ 358 /* XXX: check error code? Is there any thing I can do? */
351 (void) nilfs_ifile_delete_inode(sbi->s_ifile, inode->i_ino); 359 (void) nilfs_ifile_delete_inode(sbi->s_ifile, inode->i_ino);
352 atomic_dec(&sbi->s_inodes_count); 360 atomic_dec(&sbi->s_inodes_count);
@@ -451,7 +459,7 @@ static int __nilfs_read_inode(struct super_block *sb, unsigned long ino,
451 inode->i_op = &nilfs_special_inode_operations; 459 inode->i_op = &nilfs_special_inode_operations;
452 init_special_inode( 460 init_special_inode(
453 inode, inode->i_mode, 461 inode, inode->i_mode,
454 new_decode_dev(le64_to_cpu(raw_inode->i_device_code))); 462 huge_decode_dev(le64_to_cpu(raw_inode->i_device_code)));
455 } 463 }
456 nilfs_ifile_unmap_inode(sbi->s_ifile, ino, bh); 464 nilfs_ifile_unmap_inode(sbi->s_ifile, ino, bh);
457 brelse(bh); 465 brelse(bh);
@@ -511,7 +519,7 @@ void nilfs_write_inode_common(struct inode *inode,
511 nilfs_bmap_write(ii->i_bmap, raw_inode); 519 nilfs_bmap_write(ii->i_bmap, raw_inode);
512 else if (S_ISCHR(inode->i_mode) || S_ISBLK(inode->i_mode)) 520 else if (S_ISCHR(inode->i_mode) || S_ISBLK(inode->i_mode))
513 raw_inode->i_device_code = 521 raw_inode->i_device_code =
514 cpu_to_le64(new_encode_dev(inode->i_rdev)); 522 cpu_to_le64(huge_encode_dev(inode->i_rdev));
515 /* When extending inode, nilfs->ns_inode_size should be checked 523 /* When extending inode, nilfs->ns_inode_size should be checked
516 for substitutions of appended fields */ 524 for substitutions of appended fields */
517} 525}
@@ -606,16 +614,34 @@ void nilfs_truncate(struct inode *inode)
606 But truncate has no return value. */ 614 But truncate has no return value. */
607} 615}
608 616
609void nilfs_delete_inode(struct inode *inode) 617static void nilfs_clear_inode(struct inode *inode)
618{
619 struct nilfs_inode_info *ii = NILFS_I(inode);
620
621 /*
622 * Free resources allocated in nilfs_read_inode(), here.
623 */
624 BUG_ON(!list_empty(&ii->i_dirty));
625 brelse(ii->i_bh);
626 ii->i_bh = NULL;
627
628 if (test_bit(NILFS_I_BMAP, &ii->i_state))
629 nilfs_bmap_clear(ii->i_bmap);
630
631 nilfs_btnode_cache_clear(&ii->i_btnode_cache);
632}
633
634void nilfs_evict_inode(struct inode *inode)
610{ 635{
611 struct nilfs_transaction_info ti; 636 struct nilfs_transaction_info ti;
612 struct super_block *sb = inode->i_sb; 637 struct super_block *sb = inode->i_sb;
613 struct nilfs_inode_info *ii = NILFS_I(inode); 638 struct nilfs_inode_info *ii = NILFS_I(inode);
614 639
615 if (unlikely(is_bad_inode(inode))) { 640 if (inode->i_nlink || unlikely(is_bad_inode(inode))) {
616 if (inode->i_data.nrpages) 641 if (inode->i_data.nrpages)
617 truncate_inode_pages(&inode->i_data, 0); 642 truncate_inode_pages(&inode->i_data, 0);
618 clear_inode(inode); 643 end_writeback(inode);
644 nilfs_clear_inode(inode);
619 return; 645 return;
620 } 646 }
621 nilfs_transaction_begin(sb, &ti, 0); /* never fails */ 647 nilfs_transaction_begin(sb, &ti, 0); /* never fails */
@@ -625,6 +651,8 @@ void nilfs_delete_inode(struct inode *inode)
625 651
626 nilfs_truncate_bmap(ii, 0); 652 nilfs_truncate_bmap(ii, 0);
627 nilfs_mark_inode_dirty(inode); 653 nilfs_mark_inode_dirty(inode);
654 end_writeback(inode);
655 nilfs_clear_inode(inode);
628 nilfs_free_inode(inode); 656 nilfs_free_inode(inode);
629 /* nilfs_free_inode() marks inode buffer dirty */ 657 /* nilfs_free_inode() marks inode buffer dirty */
630 if (IS_SYNC(inode)) 658 if (IS_SYNC(inode))
@@ -648,14 +676,27 @@ int nilfs_setattr(struct dentry *dentry, struct iattr *iattr)
648 err = nilfs_transaction_begin(sb, &ti, 0); 676 err = nilfs_transaction_begin(sb, &ti, 0);
649 if (unlikely(err)) 677 if (unlikely(err))
650 return err; 678 return err;
651 err = inode_setattr(inode, iattr); 679
652 if (!err && (iattr->ia_valid & ATTR_MODE)) 680 if ((iattr->ia_valid & ATTR_SIZE) &&
681 iattr->ia_size != i_size_read(inode)) {
682 err = vmtruncate(inode, iattr->ia_size);
683 if (unlikely(err))
684 goto out_err;
685 }
686
687 setattr_copy(inode, iattr);
688 mark_inode_dirty(inode);
689
690 if (iattr->ia_valid & ATTR_MODE) {
653 err = nilfs_acl_chmod(inode); 691 err = nilfs_acl_chmod(inode);
654 if (likely(!err)) 692 if (unlikely(err))
655 err = nilfs_transaction_commit(sb); 693 goto out_err;
656 else 694 }
657 nilfs_transaction_abort(sb); 695
696 return nilfs_transaction_commit(sb);
658 697
698out_err:
699 nilfs_transaction_abort(sb);
659 return err; 700 return err;
660} 701}
661 702