[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]

Re: [Cluster-devel] [gfs2-utils PATCH] fsck.gfs2: File read-ahead



Hi,

On 10/07/14 17:54, Bob Peterson wrote:
Hi,

This patch introduces file read-ahead to pass1.
Why not the other passes too? Is that just because they are not checking all the indirect data?

Steve.

Regards,

Bob Peterson
Red Hat File Systems

Signed-off-by: Bob Peterson <rpeterso redhat com>
---
  gfs2/fsck/metawalk.c | 65 ++++++++++++++++++++++++++++++++++++++++++++++++++--
  gfs2/fsck/metawalk.h |  1 +
  gfs2/fsck/pass1.c    |  1 +
  3 files changed, 65 insertions(+), 2 deletions(-)

diff --git a/gfs2/fsck/metawalk.c b/gfs2/fsck/metawalk.c
index 659af4e..8da17c6 100644
--- a/gfs2/fsck/metawalk.c
+++ b/gfs2/fsck/metawalk.c
@@ -1184,6 +1184,59 @@ static void free_metalist(struct gfs2_inode *ip, osi_list_t *mlp)
  	}
  }
+static void file_ra(struct gfs2_inode *ip, struct gfs2_buffer_head *bh,
+		    int head_size, int maxptrs, int h)
+{
+	struct gfs2_sbd *sdp = ip->i_sbd;
+	uint64_t *p, sblock = 0, block;
+	int extlen = 0;
+
+	if (h + 2 == ip->i_di.di_height) {
+		p = (uint64_t *)(bh->b_data + head_size);
+		if (*p && *(p + 1)) {
+			sblock = be64_to_cpu(*p);
+			p++;
+			block = be64_to_cpu(*p);
+			extlen = block - sblock;
+			if (extlen > 1 && extlen <= maxptrs) {
+				posix_fadvise(sdp->device_fd,
+					      sblock * sdp->bsize,
+					      (extlen + 1) * sdp->bsize,
+					      POSIX_FADV_WILLNEED);
+				return;
+			}
+		}
+		extlen = 0;
+	}
+	for (p = (uint64_t *)(bh->b_data + head_size);
+	     p < (uint64_t *)(bh->b_data + sdp->bsize); p++) {
+		if (*p) {
+			if (!sblock) {
+				sblock = be64_to_cpu(*p);
+				extlen = 1;
+				continue;
+			}
+			block = be64_to_cpu(*p);
+			if (block == sblock + extlen) {
+				extlen++;
+				continue;
+			}
+		}
+		if (extlen && sblock) {
+			if (extlen > 1)
+				extlen--;
+			posix_fadvise(sdp->device_fd, sblock * sdp->bsize,
+				      extlen * sdp->bsize,
+				      POSIX_FADV_WILLNEED);
+			extlen = 0;
+			p--;
+		}
+	}
+	if (extlen)
+		posix_fadvise(sdp->device_fd, sblock * sdp->bsize,
+			      extlen * sdp->bsize, POSIX_FADV_WILLNEED);
+}
+
  /**
   * build_and_check_metalist - check a bunch of indirect blocks
   *                            This includes hash table blocks for directories
@@ -1204,6 +1257,7 @@ static int build_and_check_metalist(struct gfs2_inode *ip, osi_list_t *mlp,
  	int h, head_size, iblk_type;
  	uint64_t *ptr, block;
  	int error, was_duplicate, is_valid;
+	int maxptrs;
osi_list_add(&metabh->b_altlist, &mlp[0]); @@ -1225,13 +1279,18 @@ static int build_and_check_metalist(struct gfs2_inode *ip, osi_list_t *mlp,
  				iblk_type = GFS2_METATYPE_JD;
  			else
  				iblk_type = GFS2_METATYPE_IN;
-			if (ip->i_sbd->gfs1)
+			if (ip->i_sbd->gfs1) {
  				head_size = sizeof(struct gfs_indirect);
-			else
+				maxptrs = (ip->i_sbd->bsize - head_size) /
+					sizeof(uint64_t);
+			} else {
  				head_size = sizeof(struct gfs2_meta_header);
+				maxptrs = ip->i_sbd->sd_inptrs;
+			}
  		} else {
  			iblk_type = GFS2_METATYPE_DI;
  			head_size = sizeof(struct gfs2_dinode);
+			maxptrs = ip->i_sbd->sd_diptrs;
  		}
  		prev_list = &mlp[h - 1];
  		cur_list = &mlp[h];
@@ -1246,6 +1305,8 @@ static int build_and_check_metalist(struct gfs2_inode *ip, osi_list_t *mlp,
  				continue;
  			}
+ if (pass->readahead)
+				file_ra(ip, bh, head_size, maxptrs, h);
  			/* Now check the metadata itself */
  			for (ptr = (uint64_t *)(bh->b_data + head_size);
  			     (char *)ptr < (bh->b_data + ip->i_sbd->bsize);
diff --git a/gfs2/fsck/metawalk.h b/gfs2/fsck/metawalk.h
index 5e30bfe..a4e0676 100644
--- a/gfs2/fsck/metawalk.h
+++ b/gfs2/fsck/metawalk.h
@@ -94,6 +94,7 @@ enum meta_check_rc {
  struct metawalk_fxns {
  	void *private;
  	int invalid_meta_is_fatal;
+	int readahead;
  	int (*check_leaf_depth) (struct gfs2_inode *ip, uint64_t leaf_no,
  				 int ref_count, struct gfs2_buffer_head *lbh);
  	int (*check_leaf) (struct gfs2_inode *ip, uint64_t block,
diff --git a/gfs2/fsck/pass1.c b/gfs2/fsck/pass1.c
index 4f1b77a..fec2f64 100644
--- a/gfs2/fsck/pass1.c
+++ b/gfs2/fsck/pass1.c
@@ -1055,6 +1055,7 @@ static int rangecheck_eattr_leaf(struct gfs2_inode *ip, uint64_t block,
struct metawalk_fxns rangecheck_fxns = {
          .private = NULL,
+	.readahead = 1,
          .check_metalist = rangecheck_metadata,
          .check_data = rangecheck_data,
          .check_leaf = rangecheck_leaf,



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]