summaryrefslogtreecommitdiffstats
path: root/fs/affs/inode.c
diff options
context:
space:
mode:
authorRoman Zippel <zippel@linux-m68k.org>2008-04-29 17:02:20 +0200
committerAl Viro <viro@zeniv.linux.org.uk>2008-05-06 19:45:33 +0200
commitdca3c33652e437ed02c30ed3eca3cecd0cc00838 (patch)
tree590db1cd28a19c85532ba8ec8abf5eeb70f993ea /fs/affs/inode.c
parentMerge branch 'for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/rol... (diff)
downloadlinux-dca3c33652e437ed02c30ed3eca3cecd0cc00838.tar.xz
linux-dca3c33652e437ed02c30ed3eca3cecd0cc00838.zip
[PATCH] fix reservation discarding in affs
- remove affs_put_inode, so preallocations aren't discared unnecessarily often. - remove affs_drop_inode, it's called with a spinlock held, so it can't use a mutex. - make i_opencnt atomic - avoid direct b_count manipulations - a few allocation failure fixes, so that these are more gracefully handled now. Signed-off-by: Roman Zippel <zippel@linux-m68k.org> Signed-off-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Diffstat (limited to 'fs/affs/inode.c')
-rw-r--r--fs/affs/inode.c34
1 files changed, 8 insertions, 26 deletions
diff --git a/fs/affs/inode.c b/fs/affs/inode.c
index 27fe6cbe43ae..a13b334a3910 100644
--- a/fs/affs/inode.c
+++ b/fs/affs/inode.c
@@ -58,7 +58,7 @@ struct inode *affs_iget(struct super_block *sb, unsigned long ino)
AFFS_I(inode)->i_extcnt = 1;
AFFS_I(inode)->i_ext_last = ~1;
AFFS_I(inode)->i_protect = prot;
- AFFS_I(inode)->i_opencnt = 0;
+ atomic_set(&AFFS_I(inode)->i_opencnt, 0);
AFFS_I(inode)->i_blkcnt = 0;
AFFS_I(inode)->i_lc = NULL;
AFFS_I(inode)->i_lc_size = 0;
@@ -108,8 +108,6 @@ struct inode *affs_iget(struct super_block *sb, unsigned long ino)
inode->i_mode |= S_IFDIR;
} else
inode->i_mode = S_IRUGO | S_IXUGO | S_IWUSR | S_IFDIR;
- if (tail->link_chain)
- inode->i_nlink = 2;
/* Maybe it should be controlled by mount parameter? */
//inode->i_mode |= S_ISVTX;
inode->i_op = &affs_dir_inode_operations;
@@ -245,31 +243,12 @@ out:
}
void
-affs_put_inode(struct inode *inode)
-{
- pr_debug("AFFS: put_inode(ino=%lu, nlink=%u)\n", inode->i_ino, inode->i_nlink);
- affs_free_prealloc(inode);
-}
-
-void
-affs_drop_inode(struct inode *inode)
-{
- mutex_lock(&inode->i_mutex);
- if (inode->i_size != AFFS_I(inode)->mmu_private)
- affs_truncate(inode);
- mutex_unlock(&inode->i_mutex);
-
- generic_drop_inode(inode);
-}
-
-void
affs_delete_inode(struct inode *inode)
{
pr_debug("AFFS: delete_inode(ino=%lu, nlink=%u)\n", inode->i_ino, inode->i_nlink);
truncate_inode_pages(&inode->i_data, 0);
inode->i_size = 0;
- if (S_ISREG(inode->i_mode))
- affs_truncate(inode);
+ affs_truncate(inode);
clear_inode(inode);
affs_free_block(inode->i_sb, inode->i_ino);
}
@@ -277,9 +256,12 @@ affs_delete_inode(struct inode *inode)
void
affs_clear_inode(struct inode *inode)
{
- unsigned long cache_page = (unsigned long) AFFS_I(inode)->i_lc;
+ unsigned long cache_page;
pr_debug("AFFS: clear_inode(ino=%lu, nlink=%u)\n", inode->i_ino, inode->i_nlink);
+
+ affs_free_prealloc(inode);
+ cache_page = (unsigned long)AFFS_I(inode)->i_lc;
if (cache_page) {
pr_debug("AFFS: freeing ext cache\n");
AFFS_I(inode)->i_lc = NULL;
@@ -316,7 +298,7 @@ affs_new_inode(struct inode *dir)
inode->i_ino = block;
inode->i_nlink = 1;
inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME_SEC;
- AFFS_I(inode)->i_opencnt = 0;
+ atomic_set(&AFFS_I(inode)->i_opencnt, 0);
AFFS_I(inode)->i_blkcnt = 0;
AFFS_I(inode)->i_lc = NULL;
AFFS_I(inode)->i_lc_size = 0;
@@ -369,12 +351,12 @@ affs_add_entry(struct inode *dir, struct inode *inode, struct dentry *dentry, s3
switch (type) {
case ST_LINKFILE:
case ST_LINKDIR:
- inode_bh = bh;
retval = -ENOSPC;
block = affs_alloc_block(dir, dir->i_ino);
if (!block)
goto err;
retval = -EIO;
+ inode_bh = bh;
bh = affs_getzeroblk(sb, block);
if (!bh)
goto err;