[syslinux:elflink] xfs: Move readdir functions to another source file

syslinux-bot for Paulo Alcantara pcacjr at zytor.com
Tue Nov 27 12:57:21 PST 2012


Commit-ID:  7f421798ce904cba41a04aa29a05ae8b35c90172
Gitweb:     http://www.syslinux.org/commit/7f421798ce904cba41a04aa29a05ae8b35c90172
Author:     Paulo Alcantara <pcacjr at zytor.com>
AuthorDate: Sat, 28 Jul 2012 17:03:58 -0300
Committer:  Paulo Alcantara <pcacjr at zytor.com>
CommitDate: Sat, 28 Jul 2012 17:03:58 -0300

xfs: Move readdir functions to another source file

All readdir functions get bigger in size when lookup functions are added
to xfs_dir2.c accordingly, so we need to move them out to another source
file.

Signed-off-by: Paulo Alcantara <pcacjr at zytor.com>

---
 core/fs/xfs/xfs.c                           | 270 +-------------------------
 core/fs/xfs/xfs_readdir.c                   | 291 ++++++++++++++++++++++++++++
 core/fs/xfs/{xfs_dinode.h => xfs_readdir.h} |  15 +-
 3 files changed, 307 insertions(+), 269 deletions(-)

diff --git a/core/fs/xfs/xfs.c b/core/fs/xfs/xfs.c
index 873e84d..9bd278d 100644
--- a/core/fs/xfs/xfs.c
+++ b/core/fs/xfs/xfs.c
@@ -35,267 +35,7 @@
 #include "xfs.h"
 #include "xfs_dinode.h"
 #include "xfs_dir2.h"
-
-static int fill_dirent(struct fs_info *fs, struct dirent *dirent,
-		       uint32_t offset, xfs_ino_t ino, char *name,
-		       size_t namelen)
-{
-    xfs_dinode_t *core;
-
-    dirent->d_ino = ino;
-    dirent->d_off = offset;
-    dirent->d_reclen = offsetof(struct dirent, d_name) + namelen + 1;
-
-    core = xfs_dinode_get_core(fs, ino);
-    if (!core) {
-        xfs_error("Failed to get dinode from disk (ino 0x%llx)", ino);
-        return -1;
-    }
-
-    if (be16_to_cpu(core->di_mode) & S_IFDIR)
-	dirent->d_type = DT_DIR;
-    else if (be16_to_cpu(core->di_mode) & S_IFREG)
-	dirent->d_type = DT_REG;
-
-    memcpy(dirent->d_name, name, namelen + 1);
-
-    return 0;
-}
-
-static int xfs_fmt_local_readdir(struct file *file, struct dirent *dirent,
-				 xfs_dinode_t *core)
-{
-    xfs_dir2_sf_t *sf = (xfs_dir2_sf_t *)&core->di_literal_area[0];
-    xfs_dir2_sf_entry_t *sf_entry;
-    uint8_t count = sf->hdr.i8count ? sf->hdr.i8count : sf->hdr.count;
-    uint32_t offset = file->offset;
-    uint8_t *start_name;
-    uint8_t *end_name;
-    char *name;
-    xfs_ino_t ino;
-    struct fs_info *fs = file->fs;
-    int retval = 0;
-
-    xfs_debug("count %hhu i8count %hhu", sf->hdr.count, sf->hdr.i8count);
-
-    if (file->offset + 1 > count)
-	return -1;
-
-    file->offset++;
-
-    sf_entry = (xfs_dir2_sf_entry_t *)((uint8_t *)&sf->list[0] -
-				       (!sf->hdr.i8count ? 4 : 0));
-
-    if (file->offset - 1) {
-	offset = file->offset;
-	while (--offset) {
-	    sf_entry = (xfs_dir2_sf_entry_t *)(
-				(uint8_t *)sf_entry +
-				offsetof(struct xfs_dir2_sf_entry,
-					 name[0]) +
-				sf_entry->namelen +
-				(sf->hdr.i8count ? 8 : 4));
-	}
-    }
-
-    start_name = &sf_entry->name[0];
-    end_name = start_name + sf_entry->namelen;
-
-    name = xfs_dir2_get_entry_name(start_name, end_name);
-
-    ino = xfs_dir2_sf_get_inumber(sf, (xfs_dir2_inou_t *)(
-				      (uint8_t *)sf_entry +
-				      offsetof(struct xfs_dir2_sf_entry,
-					       name[0]) +
-				      sf_entry->namelen));
-
-    retval = fill_dirent(fs, dirent, file->offset, ino, (char *)name,
-			 end_name - start_name);
-    if (retval)
-	xfs_error("Failed to fill in dirent structure");
-
-    free(name);
-
-    return retval;
-}
-
-static int xfs_dir2_block_readdir(struct file *file, struct dirent *dirent,
-				  xfs_dinode_t *core)
-{
-    xfs_bmbt_irec_t r;
-    block_t dir_blk;
-    struct fs_info *fs = file->fs;
-    uint8_t *dirblk_buf;
-    uint8_t *p;
-    uint32_t offset;
-    xfs_dir2_data_hdr_t *hdr;
-    xfs_dir2_block_tail_t *btp;
-    xfs_dir2_data_unused_t *dup;
-    xfs_dir2_data_entry_t *dep;
-    uint8_t *start_name;
-    uint8_t *end_name;
-    char *name;
-    xfs_ino_t ino;
-    int retval = 0;
-
-    bmbt_irec_get(&r, (xfs_bmbt_rec_t *)&core->di_literal_area[0]);
-    dir_blk = fsblock_to_bytes(fs, r.br_startblock) >> BLOCK_SHIFT(fs);
-
-    dirblk_buf = xfs_dir2_get_dirblks(fs, dir_blk, r.br_blockcount);
-    hdr = (xfs_dir2_data_hdr_t *)dirblk_buf;
-    if (be32_to_cpu(hdr->magic) != XFS_DIR2_BLOCK_MAGIC) {
-        xfs_error("Block directory header's magic number does not match!");
-        xfs_debug("hdr->magic: 0x%lx", be32_to_cpu(hdr->magic));
-
-	free(dirblk_buf);
-
-	return -1;
-    }
-
-    btp = xfs_dir2_block_tail_p(XFS_INFO(fs), hdr);
-
-    if (file->offset + 1 > be32_to_cpu(btp->count))
-	return -1;
-
-    file->offset++;
-
-    p = (uint8_t *)(hdr + 1);
-
-    if (file->offset - 1) {
-	offset = file->offset;
-	while (--offset) {
-	    dep = (xfs_dir2_data_entry_t *)p;
-
-	    dup = (xfs_dir2_data_unused_t *)p;
-	    if (be16_to_cpu(dup->freetag) == XFS_DIR2_DATA_FREE_TAG) {
-		p += be16_to_cpu(dup->length);
-		continue;
-	    }
-
-	    p += xfs_dir2_data_entsize(dep->namelen);
-	}
-    }
-
-    dep = (xfs_dir2_data_entry_t *)p;
-
-    start_name = &dep->name[0];
-    end_name = start_name + dep->namelen;
-    name = xfs_dir2_get_entry_name(start_name, end_name);
-
-    ino = be64_to_cpu(dep->inumber);
-
-    retval = fill_dirent(fs, dirent, file->offset, ino, name,
-			 end_name - start_name);
-    if (retval)
-	xfs_error("Failed to fill in dirent structure");
-
-    free(dirblk_buf);
-    free(name);
-
-    return retval;
-}
-
-static int xfs_dir2_leaf_readdir(struct file *file, struct dirent *dirent,
-				 xfs_dinode_t *core)
-{
-    xfs_bmbt_irec_t irec;
-    struct fs_info *fs = file->fs;
-    xfs_dir2_leaf_t *leaf;
-    block_t leaf_blk, dir_blk;
-    xfs_dir2_leaf_entry_t *lep;
-    uint32_t newdb;
-    uint32_t curdb = -1;
-    xfs_dir2_data_entry_t *dep;
-    xfs_dir2_data_hdr_t *data_hdr;
-    uint8_t *start_name;
-    uint8_t *end_name;
-    char *name;
-    xfs_intino_t ino;
-    uint8_t *buf = NULL;
-    int retval = 0;
-
-    bmbt_irec_get(&irec, ((xfs_bmbt_rec_t *)&core->di_literal_area[0]) +
-					be32_to_cpu(core->di_nextents) - 1);
-    leaf_blk = fsblock_to_bytes(fs, irec.br_startblock) >>
-					BLOCK_SHIFT(file->fs);
-
-    leaf = (xfs_dir2_leaf_t *)xfs_dir2_get_dirblks(fs, leaf_blk,
-						   irec.br_blockcount);
-    if (be16_to_cpu(leaf->hdr.info.magic) != XFS_DIR2_LEAF1_MAGIC) {
-        xfs_error("Single leaf block header's magic number does not match!");
-        goto out;
-    }
-
-    if (!leaf->hdr.count)
-        goto out;
-
-    if (file->offset + 1 > be16_to_cpu(leaf->hdr.count))
-	goto out;
-
-    lep = &leaf->ents[file->offset++];
-
-    /* Skip over stale leaf entries */
-    for ( ; be32_to_cpu(lep->address) == XFS_DIR2_NULL_DATAPTR;
-	  lep++, file->offset++);
-
-    newdb = xfs_dir2_dataptr_to_db(fs, be32_to_cpu(lep->address));
-    if (newdb != curdb) {
-	if (buf)
-	    free(buf);
-
-	bmbt_irec_get(&irec,
-		      ((xfs_bmbt_rec_t *)&core->di_literal_area[0]) + newdb);
-	dir_blk = fsblock_to_bytes(fs, irec.br_startblock) >>
-						BLOCK_SHIFT(fs);
-	buf = xfs_dir2_get_dirblks(fs, dir_blk, irec.br_blockcount);
-	data_hdr = (xfs_dir2_data_hdr_t *)buf;
-	if (be32_to_cpu(data_hdr->magic) != XFS_DIR2_DATA_MAGIC) {
-	    xfs_error("Leaf directory's data magic number does not match!");
-	    goto out1;
-	}
-
-	curdb = newdb;
-    }
-
-    dep = (xfs_dir2_data_entry_t *)(
-	(char *)buf + xfs_dir2_dataptr_to_off(fs,
-					      be32_to_cpu(lep->address)));
-
-    start_name = &dep->name[0];
-    end_name = start_name + dep->namelen;
-    name = xfs_dir2_get_entry_name(start_name, end_name);
-
-    ino = be64_to_cpu(dep->inumber);
-
-    retval = fill_dirent(fs, dirent, file->offset, ino, name,
-			 end_name - start_name);
-    if (retval)
-	xfs_error("Failed to fill in dirent structure");
-
-    free(name);
-    free(buf);
-    free(leaf);
-
-    return retval;
-
-out1:
-    free(buf);
-
-out:
-    free(leaf);
-
-    return -1;
-}
-
-static int xfs_dir2_node_readdir(struct file *file, struct dirent *dirent,
-				 xfs_dinode_t *core)
-{
-    (void)file;
-    (void)dirent;
-    (void)core;
-
-    return -1;
-}
+#include "xfs_readdir.h"
 
 static int xfs_fmt_extents_readdir(struct file *file, struct dirent *dirent,
 				   xfs_dinode_t *core)
@@ -304,13 +44,13 @@ static int xfs_fmt_extents_readdir(struct file *file, struct dirent *dirent,
 
     if (be32_to_cpu(core->di_nextents) <= 1) {
 	/* Single-block Directories */
-	retval = xfs_dir2_block_readdir(file, dirent, core);
+	retval = xfs_readdir_dir2_block(file, dirent, core);
     } else if (xfs_dir2_isleaf(file->fs, core)) {
 	/* Leaf Directory */
-	retval = xfs_dir2_leaf_readdir(file, dirent, core);
+	retval = xfs_readdir_dir2_leaf(file, dirent, core);
     } else {
 	/* Node Directory */
-	retval = xfs_dir2_node_readdir(file, dirent, core);
+	retval = xfs_readdir_dir2_node(file, dirent, core);
     }
 
     return retval;
@@ -330,7 +70,7 @@ static int xfs_readdir(struct file *file, struct dirent *dirent)
     }
 
     if (core->di_format == XFS_DINODE_FMT_LOCAL)
-	retval = xfs_fmt_local_readdir(file, dirent, core);
+	retval = xfs_readdir_dir2_local(file, dirent, core);
     else if (core->di_format == XFS_DINODE_FMT_EXTENTS)
 	retval = xfs_fmt_extents_readdir(file, dirent, core);
 
diff --git a/core/fs/xfs/xfs_readdir.c b/core/fs/xfs/xfs_readdir.c
new file mode 100644
index 0000000..4eaeae3
--- /dev/null
+++ b/core/fs/xfs/xfs_readdir.c
@@ -0,0 +1,291 @@
+/*
+ * Copyright (c) 2012 Paulo Alcantara <pcacjr at zytor.com>
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it would be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write the Free Software Foundation,
+ * Inc.,  51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+ */
+
+#include <cache.h>
+#include <core.h>
+#include <fs.h>
+
+#include "xfs_types.h"
+#include "xfs_sb.h"
+#include "xfs_ag.h"
+#include "misc.h"
+#include "xfs.h"
+#include "xfs_dinode.h"
+#include "xfs_dir2.h"
+
+#include "xfs_readdir.h"
+
+static int fill_dirent(struct fs_info *fs, struct dirent *dirent,
+		       uint32_t offset, xfs_ino_t ino, char *name,
+		       size_t namelen)
+{
+    xfs_dinode_t *core;
+
+    dirent->d_ino = ino;
+    dirent->d_off = offset;
+    dirent->d_reclen = offsetof(struct dirent, d_name) + namelen + 1;
+
+    core = xfs_dinode_get_core(fs, ino);
+    if (!core) {
+        xfs_error("Failed to get dinode from disk (ino 0x%llx)", ino);
+        return -1;
+    }
+
+    if (be16_to_cpu(core->di_mode) & S_IFDIR)
+	dirent->d_type = DT_DIR;
+    else if (be16_to_cpu(core->di_mode) & S_IFREG)
+	dirent->d_type = DT_REG;
+
+    memcpy(dirent->d_name, name, namelen + 1);
+
+    return 0;
+}
+
+int xfs_readdir_dir2_local(struct file *file, struct dirent *dirent,
+			   xfs_dinode_t *core)
+{
+    xfs_dir2_sf_t *sf = (xfs_dir2_sf_t *)&core->di_literal_area[0];
+    xfs_dir2_sf_entry_t *sf_entry;
+    uint8_t count = sf->hdr.i8count ? sf->hdr.i8count : sf->hdr.count;
+    uint32_t offset = file->offset;
+    uint8_t *start_name;
+    uint8_t *end_name;
+    char *name;
+    xfs_ino_t ino;
+    struct fs_info *fs = file->fs;
+    int retval = 0;
+
+    xfs_debug("count %hhu i8count %hhu", sf->hdr.count, sf->hdr.i8count);
+
+    if (file->offset + 1 > count)
+	return -1;
+
+    file->offset++;
+
+    sf_entry = (xfs_dir2_sf_entry_t *)((uint8_t *)&sf->list[0] -
+				       (!sf->hdr.i8count ? 4 : 0));
+
+    if (file->offset - 1) {
+	offset = file->offset;
+	while (--offset) {
+	    sf_entry = (xfs_dir2_sf_entry_t *)(
+				(uint8_t *)sf_entry +
+				offsetof(struct xfs_dir2_sf_entry,
+					 name[0]) +
+				sf_entry->namelen +
+				(sf->hdr.i8count ? 8 : 4));
+	}
+    }
+
+    start_name = &sf_entry->name[0];
+    end_name = start_name + sf_entry->namelen;
+
+    name = xfs_dir2_get_entry_name(start_name, end_name);
+
+    ino = xfs_dir2_sf_get_inumber(sf, (xfs_dir2_inou_t *)(
+				      (uint8_t *)sf_entry +
+				      offsetof(struct xfs_dir2_sf_entry,
+					       name[0]) +
+				      sf_entry->namelen));
+
+    retval = fill_dirent(fs, dirent, file->offset, ino, (char *)name,
+			 end_name - start_name);
+    if (retval)
+	xfs_error("Failed to fill in dirent structure");
+
+    free(name);
+
+    return retval;
+}
+
+int xfs_readdir_dir2_block(struct file *file, struct dirent *dirent,
+			   xfs_dinode_t *core)
+{
+    xfs_bmbt_irec_t r;
+    block_t dir_blk;
+    struct fs_info *fs = file->fs;
+    uint8_t *dirblk_buf;
+    uint8_t *p;
+    uint32_t offset;
+    xfs_dir2_data_hdr_t *hdr;
+    xfs_dir2_block_tail_t *btp;
+    xfs_dir2_data_unused_t *dup;
+    xfs_dir2_data_entry_t *dep;
+    uint8_t *start_name;
+    uint8_t *end_name;
+    char *name;
+    xfs_ino_t ino;
+    int retval = 0;
+
+    bmbt_irec_get(&r, (xfs_bmbt_rec_t *)&core->di_literal_area[0]);
+    dir_blk = fsblock_to_bytes(fs, r.br_startblock) >> BLOCK_SHIFT(fs);
+
+    dirblk_buf = xfs_dir2_get_dirblks(fs, dir_blk, r.br_blockcount);
+    hdr = (xfs_dir2_data_hdr_t *)dirblk_buf;
+    if (be32_to_cpu(hdr->magic) != XFS_DIR2_BLOCK_MAGIC) {
+        xfs_error("Block directory header's magic number does not match!");
+        xfs_debug("hdr->magic: 0x%lx", be32_to_cpu(hdr->magic));
+
+	free(dirblk_buf);
+
+	return -1;
+    }
+
+    btp = xfs_dir2_block_tail_p(XFS_INFO(fs), hdr);
+
+    if (file->offset + 1 > be32_to_cpu(btp->count))
+	return -1;
+
+    file->offset++;
+
+    p = (uint8_t *)(hdr + 1);
+
+    if (file->offset - 1) {
+	offset = file->offset;
+	while (--offset) {
+	    dep = (xfs_dir2_data_entry_t *)p;
+
+	    dup = (xfs_dir2_data_unused_t *)p;
+	    if (be16_to_cpu(dup->freetag) == XFS_DIR2_DATA_FREE_TAG) {
+		p += be16_to_cpu(dup->length);
+		continue;
+	    }
+
+	    p += xfs_dir2_data_entsize(dep->namelen);
+	}
+    }
+
+    dep = (xfs_dir2_data_entry_t *)p;
+
+    start_name = &dep->name[0];
+    end_name = start_name + dep->namelen;
+    name = xfs_dir2_get_entry_name(start_name, end_name);
+
+    ino = be64_to_cpu(dep->inumber);
+
+    retval = fill_dirent(fs, dirent, file->offset, ino, name,
+			 end_name - start_name);
+    if (retval)
+	xfs_error("Failed to fill in dirent structure");
+
+    free(dirblk_buf);
+    free(name);
+
+    return retval;
+}
+
+int xfs_readdir_dir2_leaf(struct file *file, struct dirent *dirent,
+			  xfs_dinode_t *core)
+{
+    xfs_bmbt_irec_t irec;
+    struct fs_info *fs = file->fs;
+    xfs_dir2_leaf_t *leaf;
+    block_t leaf_blk, dir_blk;
+    xfs_dir2_leaf_entry_t *lep;
+    uint32_t newdb;
+    uint32_t curdb = -1;
+    xfs_dir2_data_entry_t *dep;
+    xfs_dir2_data_hdr_t *data_hdr;
+    uint8_t *start_name;
+    uint8_t *end_name;
+    char *name;
+    xfs_intino_t ino;
+    uint8_t *buf = NULL;
+    int retval = 0;
+
+    bmbt_irec_get(&irec, ((xfs_bmbt_rec_t *)&core->di_literal_area[0]) +
+					be32_to_cpu(core->di_nextents) - 1);
+    leaf_blk = fsblock_to_bytes(fs, irec.br_startblock) >>
+					BLOCK_SHIFT(file->fs);
+
+    leaf = (xfs_dir2_leaf_t *)xfs_dir2_get_dirblks(fs, leaf_blk,
+						   irec.br_blockcount);
+    if (be16_to_cpu(leaf->hdr.info.magic) != XFS_DIR2_LEAF1_MAGIC) {
+        xfs_error("Single leaf block header's magic number does not match!");
+        goto out;
+    }
+
+    if (!leaf->hdr.count)
+        goto out;
+
+    if (file->offset + 1 > be16_to_cpu(leaf->hdr.count))
+	goto out;
+
+    lep = &leaf->ents[file->offset++];
+
+    /* Skip over stale leaf entries */
+    for ( ; be32_to_cpu(lep->address) == XFS_DIR2_NULL_DATAPTR;
+	  lep++, file->offset++);
+
+    newdb = xfs_dir2_dataptr_to_db(fs, be32_to_cpu(lep->address));
+    if (newdb != curdb) {
+	if (buf)
+	    free(buf);
+
+	bmbt_irec_get(&irec,
+		      ((xfs_bmbt_rec_t *)&core->di_literal_area[0]) + newdb);
+	dir_blk = fsblock_to_bytes(fs, irec.br_startblock) >>
+						BLOCK_SHIFT(fs);
+	buf = xfs_dir2_get_dirblks(fs, dir_blk, irec.br_blockcount);
+	data_hdr = (xfs_dir2_data_hdr_t *)buf;
+	if (be32_to_cpu(data_hdr->magic) != XFS_DIR2_DATA_MAGIC) {
+	    xfs_error("Leaf directory's data magic number does not match!");
+	    goto out1;
+	}
+
+	curdb = newdb;
+    }
+
+    dep = (xfs_dir2_data_entry_t *)(
+	(char *)buf + xfs_dir2_dataptr_to_off(fs,
+					      be32_to_cpu(lep->address)));
+
+    start_name = &dep->name[0];
+    end_name = start_name + dep->namelen;
+    name = xfs_dir2_get_entry_name(start_name, end_name);
+
+    ino = be64_to_cpu(dep->inumber);
+
+    retval = fill_dirent(fs, dirent, file->offset, ino, name,
+			 end_name - start_name);
+    if (retval)
+	xfs_error("Failed to fill in dirent structure");
+
+    free(name);
+    free(buf);
+    free(leaf);
+
+    return retval;
+
+out1:
+    free(buf);
+
+out:
+    free(leaf);
+
+    return -1;
+}
+
+int xfs_readdir_dir2_node(struct file *file, struct dirent *dirent,
+			  xfs_dinode_t *core)
+{
+    (void)file;
+    (void)dirent;
+    (void)core;
+
+    return -1;
+}
diff --git a/core/fs/xfs/xfs_dinode.h b/core/fs/xfs/xfs_readdir.h
similarity index 60%
copy from core/fs/xfs/xfs_dinode.h
copy to core/fs/xfs/xfs_readdir.h
index 80deec7..2e564ec 100644
--- a/core/fs/xfs/xfs_dinode.h
+++ b/core/fs/xfs/xfs_readdir.h
@@ -15,9 +15,16 @@
  * Inc.,  51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
  */
 
-#ifndef XFS_DINODE_H_
-#define XFS_DINODE_H_
+#ifndef XFS_READDIR_H_
+#define XFS_READDIR_H_
 
-xfs_dinode_t *xfs_dinode_get_core(struct fs_info *fs, xfs_ino_t ino);
+int xfs_readdir_dir2_local(struct file *file, struct dirent *dirent,
+			   xfs_dinode_t *core);
+int xfs_readdir_dir2_block(struct file *file, struct dirent *dirent,
+			   xfs_dinode_t *core);
+int xfs_readdir_dir2_leaf(struct file *file, struct dirent *dirent,
+			  xfs_dinode_t *core);
+int xfs_readdir_dir2_node(struct file *file, struct dirent *dirent,
+			  xfs_dinode_t *core);
 
-#endif /* XFS_DINODE_H_ */
+#endif /* XFS_READDIR_H_ */


More information about the Syslinux-commits mailing list