aboutsummaryrefslogtreecommitdiffstats
path: root/fs/jffs2
diff options
context:
space:
mode:
authorThomas Gleixner <tglx@mtd.linutronix.de>2005-11-29 10:57:17 -0500
committerThomas Gleixner <tglx@mtd.linutronix.de>2005-11-29 10:57:17 -0500
commit21eeb7aa116b1f59fc23339521173cbb13e57f1a (patch)
treeaca16132a18dca8c8bf3417d118ad9d98834db32 /fs/jffs2
parentbc4117f8767203927e78b92e9e5b3ddb71d6a84d (diff)
[JFFS2] Fix the slab cache constructor of 'struct jffs2_inode_info' objects.
JFFS2 initialize f->sem mutex as "locked" in the slab constructor which is a bug. Objects are freed with unlocked f->sem mutex. So, when they allocated again, f->sem is unlocked because the slab cache constructor is not called for them. The constructor is called only once when memory pages are allocated for objects (namely, when the slab layer allocates new slabs). So, sometimes 'struct jffs2_inode_info' are allocated with unlocked f->sem, sometimes with locked. This is a bug. Instead, initialize f->sem as unlocked in the constructor. I.e., in the "constructed" state f->sem must be unlocked. From: Keijiro Yano <keijiro_yano@yahoo.co.jp> Acked-by: Artem B. Bityutskiy <dedekind@infradead.org> Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
Diffstat (limited to 'fs/jffs2')
-rw-r--r--fs/jffs2/fs.c2
-rw-r--r--fs/jffs2/super.c2
2 files changed, 3 insertions, 1 deletions
diff --git a/fs/jffs2/fs.c b/fs/jffs2/fs.c
index 543420665c5b..d0fcc5f3497e 100644
--- a/fs/jffs2/fs.c
+++ b/fs/jffs2/fs.c
@@ -234,6 +234,7 @@ void jffs2_read_inode (struct inode *inode)
234 c = JFFS2_SB_INFO(inode->i_sb); 234 c = JFFS2_SB_INFO(inode->i_sb);
235 235
236 jffs2_init_inode_info(f); 236 jffs2_init_inode_info(f);
237 down(&f->sem);
237 238
238 ret = jffs2_do_read_inode(c, f, inode->i_ino, &latest_node); 239 ret = jffs2_do_read_inode(c, f, inode->i_ino, &latest_node);
239 240
@@ -400,6 +401,7 @@ struct inode *jffs2_new_inode (struct inode *dir_i, int mode, struct jffs2_raw_i
400 401
401 f = JFFS2_INODE_INFO(inode); 402 f = JFFS2_INODE_INFO(inode);
402 jffs2_init_inode_info(f); 403 jffs2_init_inode_info(f);
404 down(&f->sem);
403 405
404 memset(ri, 0, sizeof(*ri)); 406 memset(ri, 0, sizeof(*ri));
405 /* Set OS-specific defaults for new inodes */ 407 /* Set OS-specific defaults for new inodes */
diff --git a/fs/jffs2/super.c b/fs/jffs2/super.c
index 9e0b5458d9c0..93883817cbd0 100644
--- a/fs/jffs2/super.c
+++ b/fs/jffs2/super.c
@@ -51,7 +51,7 @@ static void jffs2_i_init_once(void * foo, kmem_cache_t * cachep, unsigned long f
51 51
52 if ((flags & (SLAB_CTOR_VERIFY|SLAB_CTOR_CONSTRUCTOR)) == 52 if ((flags & (SLAB_CTOR_VERIFY|SLAB_CTOR_CONSTRUCTOR)) ==
53 SLAB_CTOR_CONSTRUCTOR) { 53 SLAB_CTOR_CONSTRUCTOR) {
54 init_MUTEX_LOCKED(&ei->sem); 54 init_MUTEX(&ei->sem);
55 inode_init_once(&ei->vfs_inode); 55 inode_init_once(&ei->vfs_inode);
56 } 56 }
57} 57}