aboutsummaryrefslogtreecommitdiffstats
path: root/fs/ocfs2/inode.c
diff options
context:
space:
mode:
Diffstat (limited to 'fs/ocfs2/inode.c')
-rw-r--r--fs/ocfs2/inode.c87
1 files changed, 31 insertions, 56 deletions
diff --git a/fs/ocfs2/inode.c b/fs/ocfs2/inode.c
index 7e9e4c79aec7..4903688f72a9 100644
--- a/fs/ocfs2/inode.c
+++ b/fs/ocfs2/inode.c
@@ -49,6 +49,7 @@
49#include "symlink.h" 49#include "symlink.h"
50#include "sysfile.h" 50#include "sysfile.h"
51#include "uptodate.h" 51#include "uptodate.h"
52#include "xattr.h"
52 53
53#include "buffer_head_io.h" 54#include "buffer_head_io.h"
54 55
@@ -219,6 +220,7 @@ int ocfs2_populate_inode(struct inode *inode, struct ocfs2_dinode *fe,
219 struct super_block *sb; 220 struct super_block *sb;
220 struct ocfs2_super *osb; 221 struct ocfs2_super *osb;
221 int status = -EINVAL; 222 int status = -EINVAL;
223 int use_plocks = 1;
222 224
223 mlog_entry("(0x%p, size:%llu)\n", inode, 225 mlog_entry("(0x%p, size:%llu)\n", inode,
224 (unsigned long long)le64_to_cpu(fe->i_size)); 226 (unsigned long long)le64_to_cpu(fe->i_size));
@@ -226,6 +228,10 @@ int ocfs2_populate_inode(struct inode *inode, struct ocfs2_dinode *fe,
226 sb = inode->i_sb; 228 sb = inode->i_sb;
227 osb = OCFS2_SB(sb); 229 osb = OCFS2_SB(sb);
228 230
231 if ((osb->s_mount_opt & OCFS2_MOUNT_LOCALFLOCKS) ||
232 ocfs2_mount_local(osb) || !ocfs2_stack_supports_plocks())
233 use_plocks = 0;
234
229 /* this means that read_inode cannot create a superblock inode 235 /* this means that read_inode cannot create a superblock inode
230 * today. change if needed. */ 236 * today. change if needed. */
231 if (!OCFS2_IS_VALID_DINODE(fe) || 237 if (!OCFS2_IS_VALID_DINODE(fe) ||
@@ -295,13 +301,19 @@ int ocfs2_populate_inode(struct inode *inode, struct ocfs2_dinode *fe,
295 301
296 switch (inode->i_mode & S_IFMT) { 302 switch (inode->i_mode & S_IFMT) {
297 case S_IFREG: 303 case S_IFREG:
298 inode->i_fop = &ocfs2_fops; 304 if (use_plocks)
305 inode->i_fop = &ocfs2_fops;
306 else
307 inode->i_fop = &ocfs2_fops_no_plocks;
299 inode->i_op = &ocfs2_file_iops; 308 inode->i_op = &ocfs2_file_iops;
300 i_size_write(inode, le64_to_cpu(fe->i_size)); 309 i_size_write(inode, le64_to_cpu(fe->i_size));
301 break; 310 break;
302 case S_IFDIR: 311 case S_IFDIR:
303 inode->i_op = &ocfs2_dir_iops; 312 inode->i_op = &ocfs2_dir_iops;
304 inode->i_fop = &ocfs2_dops; 313 if (use_plocks)
314 inode->i_fop = &ocfs2_dops;
315 else
316 inode->i_fop = &ocfs2_dops_no_plocks;
305 i_size_write(inode, le64_to_cpu(fe->i_size)); 317 i_size_write(inode, le64_to_cpu(fe->i_size));
306 break; 318 break;
307 case S_IFLNK: 319 case S_IFLNK:
@@ -448,8 +460,11 @@ static int ocfs2_read_locked_inode(struct inode *inode,
448 } 460 }
449 } 461 }
450 462
451 status = ocfs2_read_block(osb, args->fi_blkno, &bh, 0, 463 if (can_lock)
452 can_lock ? inode : NULL); 464 status = ocfs2_read_blocks(inode, args->fi_blkno, 1, &bh,
465 OCFS2_BH_IGNORE_CACHE);
466 else
467 status = ocfs2_read_blocks_sync(osb, args->fi_blkno, 1, &bh);
453 if (status < 0) { 468 if (status < 0) {
454 mlog_errno(status); 469 mlog_errno(status);
455 goto bail; 470 goto bail;
@@ -522,6 +537,9 @@ static int ocfs2_truncate_for_delete(struct ocfs2_super *osb,
522 * data and fast symlinks. 537 * data and fast symlinks.
523 */ 538 */
524 if (fe->i_clusters) { 539 if (fe->i_clusters) {
540 if (ocfs2_should_order_data(inode))
541 ocfs2_begin_ordered_truncate(inode, 0);
542
525 handle = ocfs2_start_trans(osb, OCFS2_INODE_UPDATE_CREDITS); 543 handle = ocfs2_start_trans(osb, OCFS2_INODE_UPDATE_CREDITS);
526 if (IS_ERR(handle)) { 544 if (IS_ERR(handle)) {
527 status = PTR_ERR(handle); 545 status = PTR_ERR(handle);
@@ -730,6 +748,13 @@ static int ocfs2_wipe_inode(struct inode *inode,
730 goto bail_unlock_dir; 748 goto bail_unlock_dir;
731 } 749 }
732 750
751 /*Free extended attribute resources associated with this inode.*/
752 status = ocfs2_xattr_remove(inode, di_bh);
753 if (status < 0) {
754 mlog_errno(status);
755 goto bail_unlock_dir;
756 }
757
733 status = ocfs2_remove_inode(inode, di_bh, orphan_dir_inode, 758 status = ocfs2_remove_inode(inode, di_bh, orphan_dir_inode,
734 orphan_dir_bh); 759 orphan_dir_bh);
735 if (status < 0) 760 if (status < 0)
@@ -1081,6 +1106,8 @@ void ocfs2_clear_inode(struct inode *inode)
1081 oi->ip_last_trans = 0; 1106 oi->ip_last_trans = 0;
1082 oi->ip_dir_start_lookup = 0; 1107 oi->ip_dir_start_lookup = 0;
1083 oi->ip_blkno = 0ULL; 1108 oi->ip_blkno = 0ULL;
1109 jbd2_journal_release_jbd_inode(OCFS2_SB(inode->i_sb)->journal->j_journal,
1110 &oi->ip_jinode);
1084 1111
1085bail: 1112bail:
1086 mlog_exit_void(); 1113 mlog_exit_void();
@@ -1107,58 +1134,6 @@ void ocfs2_drop_inode(struct inode *inode)
1107} 1134}
1108 1135
1109/* 1136/*
1110 * TODO: this should probably be merged into ocfs2_get_block
1111 *
1112 * However, you now need to pay attention to the cont_prepare_write()
1113 * stuff in ocfs2_get_block (that is, ocfs2_get_block pretty much
1114 * expects never to extend).
1115 */
1116struct buffer_head *ocfs2_bread(struct inode *inode,
1117 int block, int *err, int reada)
1118{
1119 struct buffer_head *bh = NULL;
1120 int tmperr;
1121 u64 p_blkno;
1122 int readflags = OCFS2_BH_CACHED;
1123
1124 if (reada)
1125 readflags |= OCFS2_BH_READAHEAD;
1126
1127 if (((u64)block << inode->i_sb->s_blocksize_bits) >=
1128 i_size_read(inode)) {
1129 BUG_ON(!reada);
1130 return NULL;
1131 }
1132
1133 down_read(&OCFS2_I(inode)->ip_alloc_sem);
1134 tmperr = ocfs2_extent_map_get_blocks(inode, block, &p_blkno, NULL,
1135 NULL);
1136 up_read(&OCFS2_I(inode)->ip_alloc_sem);
1137 if (tmperr < 0) {
1138 mlog_errno(tmperr);
1139 goto fail;
1140 }
1141
1142 tmperr = ocfs2_read_block(OCFS2_SB(inode->i_sb), p_blkno, &bh,
1143 readflags, inode);
1144 if (tmperr < 0)
1145 goto fail;
1146
1147 tmperr = 0;
1148
1149 *err = 0;
1150 return bh;
1151
1152fail:
1153 if (bh) {
1154 brelse(bh);
1155 bh = NULL;
1156 }
1157 *err = -EIO;
1158 return NULL;
1159}
1160
1161/*
1162 * This is called from our getattr. 1137 * This is called from our getattr.
1163 */ 1138 */
1164int ocfs2_inode_revalidate(struct dentry *dentry) 1139int ocfs2_inode_revalidate(struct dentry *dentry)