diff options
Diffstat (limited to 'fs/gfs2/log.c')
| -rw-r--r-- | fs/gfs2/log.c | 47 | 
1 files changed, 29 insertions, 18 deletions
diff --git a/fs/gfs2/log.c b/fs/gfs2/log.c index b8830fda51e8..a2e1df488df0 100644 --- a/fs/gfs2/log.c +++ b/fs/gfs2/log.c @@ -551,9 +551,9 @@ static void gfs2_ordered_write(struct gfs2_sbd *sdp)  	LIST_HEAD(written);  	spin_lock(&sdp->sd_ordered_lock); -	list_sort(NULL, &sdp->sd_log_le_ordered, &ip_cmp); -	while (!list_empty(&sdp->sd_log_le_ordered)) { -		ip = list_entry(sdp->sd_log_le_ordered.next, struct gfs2_inode, i_ordered); +	list_sort(NULL, &sdp->sd_log_ordered, &ip_cmp); +	while (!list_empty(&sdp->sd_log_ordered)) { +		ip = list_entry(sdp->sd_log_ordered.next, struct gfs2_inode, i_ordered);  		if (ip->i_inode.i_mapping->nrpages == 0) {  			test_and_clear_bit(GIF_ORDERED, &ip->i_flags);  			list_del(&ip->i_ordered); @@ -564,7 +564,7 @@ static void gfs2_ordered_write(struct gfs2_sbd *sdp)  		filemap_fdatawrite(ip->i_inode.i_mapping);  		spin_lock(&sdp->sd_ordered_lock);  	} -	list_splice(&written, &sdp->sd_log_le_ordered); +	list_splice(&written, &sdp->sd_log_ordered);  	spin_unlock(&sdp->sd_ordered_lock);  } @@ -573,8 +573,8 @@ static void gfs2_ordered_wait(struct gfs2_sbd *sdp)  	struct gfs2_inode *ip;  	spin_lock(&sdp->sd_ordered_lock); -	while (!list_empty(&sdp->sd_log_le_ordered)) { -		ip = list_entry(sdp->sd_log_le_ordered.next, struct gfs2_inode, i_ordered); +	while (!list_empty(&sdp->sd_log_ordered)) { +		ip = list_entry(sdp->sd_log_ordered.next, struct gfs2_inode, i_ordered);  		list_del(&ip->i_ordered);  		WARN_ON(!test_and_clear_bit(GIF_ORDERED, &ip->i_flags));  		if (ip->i_inode.i_mapping->nrpages == 0) @@ -606,9 +606,12 @@ void gfs2_add_revoke(struct gfs2_sbd *sdp, struct gfs2_bufdata *bd)  	gfs2_remove_from_ail(bd); /* drops ref on bh */  	bd->bd_bh = NULL;  	sdp->sd_log_num_revoke++; -	atomic_inc(&gl->gl_revokes); +	if (!test_bit(GLF_REVOKES, &gl->gl_flags)) { +		set_bit(GLF_REVOKES, &gl->gl_flags); +		gfs2_glock_hold(gl); +	}  	set_bit(GLF_LFLUSH, &gl->gl_flags); -	list_add(&bd->bd_list, &sdp->sd_log_le_revoke); +	list_add(&bd->bd_list, &sdp->sd_log_revokes);  }  void gfs2_write_revokes(struct gfs2_sbd *sdp) @@ -666,11 +669,12 @@ out_of_blocks:  }  /** - * write_log_header - Write a journal log header buffer at sd_log_flush_head + * gfs2_write_log_header - Write a journal log header buffer at lblock   * @sdp: The GFS2 superblock   * @jd: journal descriptor of the journal to which we are writing   * @seq: sequence number   * @tail: tail of the log + * @lblock: value for lh_blkno (block number relative to start of journal)   * @flags: log header flags GFS2_LOG_HEAD_*   * @op_flags: flags to pass to the bio   * @@ -678,7 +682,8 @@ out_of_blocks:   */  void gfs2_write_log_header(struct gfs2_sbd *sdp, struct gfs2_jdesc *jd, -			   u64 seq, u32 tail, u32 flags, int op_flags) +			   u64 seq, u32 tail, u32 lblock, u32 flags, +			   int op_flags)  {  	struct gfs2_log_header *lh;  	u32 hash, crc; @@ -686,7 +691,7 @@ void gfs2_write_log_header(struct gfs2_sbd *sdp, struct gfs2_jdesc *jd,  	struct gfs2_statfs_change_host *l_sc = &sdp->sd_statfs_local;  	struct timespec64 tv;  	struct super_block *sb = sdp->sd_vfs; -	u64 addr; +	u64 dblock;  	lh = page_address(page);  	clear_page(lh); @@ -699,15 +704,21 @@ void gfs2_write_log_header(struct gfs2_sbd *sdp, struct gfs2_jdesc *jd,  	lh->lh_sequence = cpu_to_be64(seq);  	lh->lh_flags = cpu_to_be32(flags);  	lh->lh_tail = cpu_to_be32(tail); -	lh->lh_blkno = cpu_to_be32(sdp->sd_log_flush_head); +	lh->lh_blkno = cpu_to_be32(lblock);  	hash = ~crc32(~0, lh, LH_V1_SIZE);  	lh->lh_hash = cpu_to_be32(hash);  	ktime_get_coarse_real_ts64(&tv);  	lh->lh_nsec = cpu_to_be32(tv.tv_nsec);  	lh->lh_sec = cpu_to_be64(tv.tv_sec); -	addr = gfs2_log_bmap(sdp); -	lh->lh_addr = cpu_to_be64(addr); +	if (!list_empty(&jd->extent_list)) +		dblock = gfs2_log_bmap(sdp); +	else { +		int ret = gfs2_lblk_to_dblk(jd->jd_inode, lblock, &dblock); +		if (gfs2_assert_withdraw(sdp, ret == 0)) +			return; +	} +	lh->lh_addr = cpu_to_be64(dblock);  	lh->lh_jinode = cpu_to_be64(GFS2_I(jd->jd_inode)->i_no_addr);  	/* We may only write local statfs, quota, etc., when writing to our @@ -732,8 +743,8 @@ void gfs2_write_log_header(struct gfs2_sbd *sdp, struct gfs2_jdesc *jd,  		     sb->s_blocksize - LH_V1_SIZE - 4);  	lh->lh_crc = cpu_to_be32(crc); -	gfs2_log_write(sdp, page, sb->s_blocksize, 0, addr); -	gfs2_log_submit_bio(&sdp->sd_log_bio, REQ_OP_WRITE, op_flags); +	gfs2_log_write(sdp, page, sb->s_blocksize, 0, dblock); +	gfs2_log_submit_bio(&sdp->sd_log_bio, REQ_OP_WRITE | op_flags);  	log_flush_wait(sdp);  } @@ -761,7 +772,7 @@ static void log_write_header(struct gfs2_sbd *sdp, u32 flags)  	}  	sdp->sd_log_idle = (tail == sdp->sd_log_flush_head);  	gfs2_write_log_header(sdp, sdp->sd_jdesc, sdp->sd_log_sequence++, tail, -			      flags, op_flags); +			      sdp->sd_log_flush_head, flags, op_flags);  	if (sdp->sd_log_tail != tail)  		log_pull_tail(sdp, tail); @@ -810,7 +821,7 @@ void gfs2_log_flush(struct gfs2_sbd *sdp, struct gfs2_glock *gl, u32 flags)  	gfs2_ordered_write(sdp);  	lops_before_commit(sdp, tr); -	gfs2_log_submit_bio(&sdp->sd_log_bio, REQ_OP_WRITE, 0); +	gfs2_log_submit_bio(&sdp->sd_log_bio, REQ_OP_WRITE);  	if (sdp->sd_log_head != sdp->sd_log_flush_head) {  		log_flush_wait(sdp);  |