summaryrefslogtreecommitdiffstats
path: root/fs/gfs2/trans.c
diff options
context:
space:
mode:
authorSteven Whitehouse <swhiteho@redhat.com>2012-12-14 17:54:21 +0000
committerSteven Whitehouse <swhiteho@redhat.com>2013-01-29 10:28:44 +0000
commitc76c4d96bdd89027306cebc80eb3397286d8da66 (patch)
tree6e3de8b09e50d6a9fe1c690125e0a6118724de4c /fs/gfs2/trans.c
parent767f433f346959d6a09b85478eb5db133ab25c6f (diff)
downloadlinux-c76c4d96bdd89027306cebc80eb3397286d8da66.tar.gz
linux-c76c4d96bdd89027306cebc80eb3397286d8da66.tar.bz2
linux-c76c4d96bdd89027306cebc80eb3397286d8da66.zip
GFS2: Merge gfs2_attach_bufdata() into trans.c
The locking in gfs2_attach_bufdata() was type specific (data/meta) which made the function rather confusing. This patch moves the core of gfs2_attach_bufdata() into trans.c renaming it gfs2_alloc_bufdata() and moving the locking into gfs2_trans_add_data()/gfs2_trans_add_meta() As a result all of the locking related to adding data and metadata to the journal is now in these two functions. This should help to clarify what is going on, and give us some opportunities to simplify in some cases. Signed-off-by: Steven Whitehouse <swhiteho@redhat.com>
Diffstat (limited to 'fs/gfs2/trans.c')
-rw-r--r--fs/gfs2/trans.c37
1 files changed, 26 insertions, 11 deletions
diff --git a/fs/gfs2/trans.c b/fs/gfs2/trans.c
index 1fbd57eafa48..14dbf6d3cdc0 100644
--- a/fs/gfs2/trans.c
+++ b/fs/gfs2/trans.c
@@ -143,6 +143,21 @@ void gfs2_trans_end(struct gfs2_sbd *sdp)
sb_end_intwrite(sdp->sd_vfs);
}
+static struct gfs2_bufdata *gfs2_alloc_bufdata(struct gfs2_glock *gl,
+ struct buffer_head *bh,
+ const struct gfs2_log_operations *lops)
+{
+ struct gfs2_bufdata *bd;
+
+ bd = kmem_cache_zalloc(gfs2_bufdata_cachep, GFP_NOFS | __GFP_NOFAIL);
+ bd->bd_bh = bh;
+ bd->bd_gl = gl;
+ bd->bd_ops = lops;
+ INIT_LIST_HEAD(&bd->bd_list);
+ bh->b_private = bd;
+ return bd;
+}
+
/**
* databuf_lo_add - Add a databuf to the transaction.
*
@@ -190,16 +205,15 @@ void gfs2_trans_add_data(struct gfs2_glock *gl, struct buffer_head *bh)
lock_buffer(bh);
gfs2_log_lock(sdp);
bd = bh->b_private;
- if (bd)
- gfs2_assert(sdp, bd->bd_gl == gl);
- else {
+ if (bd == NULL) {
gfs2_log_unlock(sdp);
unlock_buffer(bh);
- gfs2_attach_bufdata(gl, bh, 0);
- bd = bh->b_private;
+ if (bh->b_private == NULL)
+ bd = gfs2_alloc_bufdata(gl, bh, &gfs2_databuf_lops);
lock_buffer(bh);
gfs2_log_lock(sdp);
}
+ gfs2_assert(sdp, bd->bd_gl == gl);
databuf_lo_add(sdp, bd);
gfs2_log_unlock(sdp);
unlock_buffer(bh);
@@ -240,16 +254,17 @@ void gfs2_trans_add_meta(struct gfs2_glock *gl, struct buffer_head *bh)
lock_buffer(bh);
gfs2_log_lock(sdp);
bd = bh->b_private;
- if (bd)
- gfs2_assert(sdp, bd->bd_gl == gl);
- else {
+ if (bd == NULL) {
gfs2_log_unlock(sdp);
unlock_buffer(bh);
- gfs2_attach_bufdata(gl, bh, 1);
- bd = bh->b_private;
+ lock_page(bh->b_page);
+ if (bh->b_private == NULL)
+ bd = gfs2_alloc_bufdata(gl, bh, &gfs2_buf_lops);
+ unlock_page(bh->b_page);
lock_buffer(bh);
gfs2_log_lock(sdp);
}
+ gfs2_assert(sdp, bd->bd_gl == gl);
meta_lo_add(sdp, bd);
gfs2_log_unlock(sdp);
unlock_buffer(bh);
@@ -263,7 +278,7 @@ void gfs2_trans_add_revoke(struct gfs2_sbd *sdp, struct gfs2_bufdata *bd)
BUG_ON(!list_empty(&bd->bd_list));
BUG_ON(!list_empty(&bd->bd_ail_st_list));
BUG_ON(!list_empty(&bd->bd_ail_gl_list));
- lops_init_le(bd, &gfs2_revoke_lops);
+ bd->bd_ops = &gfs2_revoke_lops;
tr->tr_touched = 1;
tr->tr_num_revoke++;
sdp->sd_log_num_revoke++;