]> git.karo-electronics.de Git - mv-sheeva.git/commitdiff
nilfs2: do not update log cursor for small change
authorRyusuke Konishi <konishi.ryusuke@lab.ntt.co.jp>
Tue, 29 Jun 2010 05:42:13 +0000 (14:42 +0900)
committerRyusuke Konishi <konishi.ryusuke@lab.ntt.co.jp>
Fri, 23 Jul 2010 01:02:11 +0000 (10:02 +0900)
Super blocks of nilfs are periodically overwritten in order to record
the recent log position.  This shortens recovery time after unclean
unmount, but the current implementation performs the update even for a
few blocks of change.  If the filesystem gets small changes slowly and
continually, super blocks may be updated excessively.

This moderates the issue by skipping update of log cursor if it does
not cross a segment boundary.

Signed-off-by: Ryusuke Konishi <konishi.ryusuke@lab.ntt.co.jp>
fs/nilfs2/segment.c
fs/nilfs2/the_nilfs.c
fs/nilfs2/the_nilfs.h

index 04e04854a3110e17cbd47a4f60cf8d30ce2e873a..9fd051a33c4f34edef3ce62a240c696d7227f285 100644 (file)
@@ -1951,7 +1951,6 @@ static void nilfs_segctor_complete_write(struct nilfs_sc_info *sci)
        if (update_sr) {
                nilfs_set_last_segment(nilfs, segbuf->sb_pseg_start,
                                       segbuf->sb_sum.seg_seq, nilfs->ns_cno++);
-               set_nilfs_sb_dirty(nilfs);
 
                clear_bit(NILFS_SC_HAVE_DELTA, &sci->sc_flags);
                clear_bit(NILFS_SC_DIRTY, &sci->sc_flags);
index 88c8976c55a9126f32a09aefe6f766a80f43b84c..f2efc8c5be7fbd6a75f7f4773b095ec9c63037d3 100644 (file)
@@ -47,6 +47,16 @@ void nilfs_set_last_segment(struct the_nilfs *nilfs,
        nilfs->ns_last_pseg = start_blocknr;
        nilfs->ns_last_seq = seq;
        nilfs->ns_last_cno = cno;
+
+       if (!nilfs_sb_dirty(nilfs)) {
+               if (nilfs->ns_prev_seq == nilfs->ns_last_seq)
+                       goto stay_cursor;
+
+               set_nilfs_sb_dirty(nilfs);
+       }
+       nilfs->ns_prev_seq = nilfs->ns_last_seq;
+
+ stay_cursor:
        spin_unlock(&nilfs->ns_last_segment_lock);
 }
 
@@ -267,6 +277,7 @@ static int nilfs_store_log_cursor(struct the_nilfs *nilfs,
        nilfs->ns_last_cno = le64_to_cpu(sbp->s_last_cno);
        nilfs->ns_last_seq = le64_to_cpu(sbp->s_last_seq);
 
+       nilfs->ns_prev_seq = nilfs->ns_last_seq;
        nilfs->ns_seg_seq = nilfs->ns_last_seq;
        nilfs->ns_segnum =
                nilfs_get_segnum_of_block(nilfs, nilfs->ns_last_pseg);
index 32b4983b745846e8cb2c0b23cf91961c90c9b789..f785a7b0ab994c55d6940f70259b53b53230325a 100644 (file)
@@ -74,6 +74,7 @@ enum {
  * @ns_last_seq: sequence value of the latest segment
  * @ns_last_cno: checkpoint number of the latest segment
  * @ns_prot_seq: least sequence number of segments which must not be reclaimed
+ * @ns_prev_seq: base sequence number used to decide if advance log cursor
  * @ns_segctor_sem: segment constructor semaphore
  * @ns_dat: DAT file inode
  * @ns_cpfile: checkpoint file inode
@@ -151,6 +152,7 @@ struct the_nilfs {
        u64                     ns_last_seq;
        __u64                   ns_last_cno;
        u64                     ns_prot_seq;
+       u64                     ns_prev_seq;
 
        struct rw_semaphore     ns_segctor_sem;