aboutsummaryrefslogtreecommitdiffstats
path: root/fs/gfs2/trans.c
diff options
context:
space:
mode:
authorSteven Whitehouse <swhiteho@redhat.com>2013-01-28 04:30:07 -0500
committerSteven Whitehouse <swhiteho@redhat.com>2013-01-29 05:29:17 -0500
commit4513899092b3254b3539f92a65d2839afa1d50f6 (patch)
tree1080b7adfac648dacd2d4aa70643a6a456284492 /fs/gfs2/trans.c
parentd564053f074634e7a966359dc97d26900fa5f52d (diff)
GFS2: Use ->writepages for ordered writes
Instead of using a list of buffers to write ahead of the journal flush, this now uses a list of inodes and calls ->writepages via filemap_fdatawrite() in order to achieve the same thing. For most use cases this results in a shorter ordered write list, as well as much larger i/os being issued. The ordered write list is sorted by inode number before writing in order to retain the disk block ordering between inodes as per the previous code. The previous ordered write code used to conflict in its assumptions about how to write out the disk blocks with mpage_writepages() so that with this updated version we can also use mpage_writepages() for GFS2's ordered write, writepages implementation. So we will also send larger i/os from writeback too. Signed-off-by: Steven Whitehouse <swhiteho@redhat.com>
Diffstat (limited to 'fs/gfs2/trans.c')
-rw-r--r--fs/gfs2/trans.c41
1 files changed, 18 insertions, 23 deletions
diff --git a/fs/gfs2/trans.c b/fs/gfs2/trans.c
index 14dbf6d3cdc0..88162fae27a5 100644
--- a/fs/gfs2/trans.c
+++ b/fs/gfs2/trans.c
@@ -159,7 +159,9 @@ static struct gfs2_bufdata *gfs2_alloc_bufdata(struct gfs2_glock *gl,
159} 159}
160 160
161/** 161/**
162 * databuf_lo_add - Add a databuf to the transaction. 162 * gfs2_trans_add_data - Add a databuf to the transaction.
163 * @gl: The inode glock associated with the buffer
164 * @bh: The buffer to add
163 * 165 *
164 * This is used in two distinct cases: 166 * This is used in two distinct cases:
165 * i) In ordered write mode 167 * i) In ordered write mode
@@ -174,33 +176,18 @@ static struct gfs2_bufdata *gfs2_alloc_bufdata(struct gfs2_glock *gl,
174 * blocks, which isn't an enormous overhead but twice as much as 176 * blocks, which isn't an enormous overhead but twice as much as
175 * for normal metadata blocks. 177 * for normal metadata blocks.
176 */ 178 */
177static void databuf_lo_add(struct gfs2_sbd *sdp, struct gfs2_bufdata *bd) 179void gfs2_trans_add_data(struct gfs2_glock *gl, struct buffer_head *bh)
178{ 180{
179 struct gfs2_trans *tr = current->journal_info; 181 struct gfs2_trans *tr = current->journal_info;
180 struct address_space *mapping = bd->bd_bh->b_page->mapping; 182 struct gfs2_sbd *sdp = gl->gl_sbd;
183 struct address_space *mapping = bh->b_page->mapping;
181 struct gfs2_inode *ip = GFS2_I(mapping->host); 184 struct gfs2_inode *ip = GFS2_I(mapping->host);
185 struct gfs2_bufdata *bd;
182 186
183 if (tr) 187 if (!gfs2_is_jdata(ip)) {
184 tr->tr_touched = 1; 188 gfs2_ordered_add_inode(ip);
185 if (!list_empty(&bd->bd_list))
186 return; 189 return;
187 set_bit(GLF_LFLUSH, &bd->bd_gl->gl_flags);
188 set_bit(GLF_DIRTY, &bd->bd_gl->gl_flags);
189 if (gfs2_is_jdata(ip)) {
190 gfs2_pin(sdp, bd->bd_bh);
191 tr->tr_num_databuf_new++;
192 sdp->sd_log_num_databuf++;
193 list_add_tail(&bd->bd_list, &sdp->sd_log_le_databuf);
194 } else {
195 list_add_tail(&bd->bd_list, &sdp->sd_log_le_ordered);
196 } 190 }
197}
198
199void gfs2_trans_add_data(struct gfs2_glock *gl, struct buffer_head *bh)
200{
201
202 struct gfs2_sbd *sdp = gl->gl_sbd;
203 struct gfs2_bufdata *bd;
204 191
205 lock_buffer(bh); 192 lock_buffer(bh);
206 gfs2_log_lock(sdp); 193 gfs2_log_lock(sdp);
@@ -214,7 +201,15 @@ void gfs2_trans_add_data(struct gfs2_glock *gl, struct buffer_head *bh)
214 gfs2_log_lock(sdp); 201 gfs2_log_lock(sdp);
215 } 202 }
216 gfs2_assert(sdp, bd->bd_gl == gl); 203 gfs2_assert(sdp, bd->bd_gl == gl);
217 databuf_lo_add(sdp, bd); 204 tr->tr_touched = 1;
205 if (list_empty(&bd->bd_list)) {
206 set_bit(GLF_LFLUSH, &bd->bd_gl->gl_flags);
207 set_bit(GLF_DIRTY, &bd->bd_gl->gl_flags);
208 gfs2_pin(sdp, bd->bd_bh);
209 tr->tr_num_databuf_new++;
210 sdp->sd_log_num_databuf++;
211 list_add_tail(&bd->bd_list, &sdp->sd_log_le_databuf);
212 }
218 gfs2_log_unlock(sdp); 213 gfs2_log_unlock(sdp);
219 unlock_buffer(bh); 214 unlock_buffer(bh);
220} 215}