Hi all,
I'm sorry that I can't send patch mail by git-send-mail because I'm in ST 
internal network. 
I just post the whole output by git-format-patch tool. 
If it's buggy, please let me know. 
Thanks!

>From 0a08bfe1f0fc864a9920501a825e6698d082f231 Mon Sep 17 00:00:00 2001
From: Ryan Chen <[EMAIL PROTECTED]>
Date: Tue, 19 Aug 2008 07:11:23 -0400
Subject: [PATCH] Optimize ext2fs read functions

---
 fs/ext2/ext2fs.c |  121 ++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 121 insertions(+), 0 deletions(-)
 mode change 100644 => 100755 fs/ext2/ext2fs.c

diff --git a/fs/ext2/ext2fs.c b/fs/ext2/ext2fs.c
old mode 100644
new mode 100755
index 7833551..f64936f
--- a/fs/ext2/ext2fs.c
+++ b/fs/ext2/ext2fs.c
@@ -29,6 +29,7 @@
 #include <ext2fs.h>
 #include <malloc.h>
 #include <asm/byteorder.h>
+#define CFG_EXT2_SUPPORT_DYNAMIC_REV
 
 extern int ext2fs_devread (int sector, int byte_offset, int byte_len,
                           char *buf);
@@ -66,6 +67,17 @@ extern int ext2fs_devread (int sector, int byte_offset, int 
byte_len,
 /* The size of an ext2 block in bytes.  */
 #define EXT2_BLOCK_SIZE(data)     (1 << LOG2_BLOCK_SIZE(data))
 
+#ifdef CFG_EXT2_SUPPORT_DYNAMIC_REV
+/*
+ * Revision levels
+ */
+#define EXT2_GOOD_OLD_REV       0       /* The good old (original) format */
+#define EXT2_DYNAMIC_REV        1       /* V2 format w/ dynamic inode sizes */
+
+#define EXT2_GOOD_OLD_INODE_SIZE 128
+uint32_t ext2_inode_size = EXT2_GOOD_OLD_INODE_SIZE;
+#endif
+
 /* The ext2 superblock.  */
 struct ext2_sblock {
        uint32_t total_inodes;
@@ -217,7 +229,11 @@ static int ext2fs_read_inode
        if (status == 0) {
                return (0);
        }
+#ifdef CFG_EXT2_SUPPORT_DYNAMIC_REV
+       inodes_per_block = EXT2_BLOCK_SIZE (data) / ext2_inode_size;
+#else
        inodes_per_block = EXT2_BLOCK_SIZE (data) / 128;
+#endif
        blkno = (ino % __le32_to_cpu (sblock->inodes_per_group)) /
                inodes_per_block;
        blkoff = (ino % __le32_to_cpu (sblock->inodes_per_group)) %
@@ -226,10 +242,17 @@ static int ext2fs_read_inode
        printf ("ext2fs read inode blkno %d blkoff %d\n", blkno, blkoff);
 #endif
        /* Read the inode.  */
+#ifdef CFG_EXT2_SUPPORT_DYNAMIC_REV
+       status = ext2fs_devread (((__le32_to_cpu (blkgrp.inode_table_id) +
+                                  blkno) << LOG2_EXT2_BLOCK_SIZE (data)),
+                                ext2_inode_size * blkoff,
+                                sizeof (struct ext2_inode), (char *) inode);
+#else
        status = ext2fs_devread (((__le32_to_cpu (blkgrp.inode_table_id) +
                                   blkno) << LOG2_EXT2_BLOCK_SIZE (data)),
                                 sizeof (struct ext2_inode) * blkoff,
                                 sizeof (struct ext2_inode), (char *) inode);
+#endif
        if (status == 0) {
                return (0);
        }
@@ -243,8 +266,13 @@ void ext2fs_free_node (ext2fs_node_t node, ext2fs_node_t 
currroot) {
        }
 }
 
+#define CFG_OPTIMIZE_EXT2_READ
 
+#ifdef CFG_OPTIMIZE_EXT2_READ
+static int ext2fs_read_block (ext2fs_node_t node, int fileblock, int *stream) {
+#else
 static int ext2fs_read_block (ext2fs_node_t node, int fileblock) {
+#endif
        struct ext2_data *data = node->data;
        struct ext2_inode *inode = &node->inode;
        int blknr;
@@ -252,9 +280,21 @@ static int ext2fs_read_block (ext2fs_node_t node, int 
fileblock) {
        int log2_blksz = LOG2_EXT2_BLOCK_SIZE (data);
        int status;
 
+#ifdef CFG_OPTIMIZE_EXT2_READ
+       *stream = 1;/* itself */
+#endif
+
        /* Direct blocks.  */
        if (fileblock < INDIRECT_BLOCKS) {
                blknr = __le32_to_cpu (inode->b.blocks.dir_blocks[fileblock]);
+#ifdef CFG_OPTIMIZE_EXT2_READ
+               while(((inode->b.blocks.dir_blocks[fileblock + 1] - 
+                       inode->b.blocks.dir_blocks[fileblock]) == 1) && \
+                       (fileblock < INDIRECT_BLOCKS - 1)) {
+                       fileblock++;
+                       *stream += 1;
+               }
+#endif
        }
        /* Indirect.  */
        else if (fileblock < (INDIRECT_BLOCKS + (blksz / 4))) {
@@ -294,6 +334,14 @@ static int ext2fs_read_block (ext2fs_node_t node, int 
fileblock) {
                }
                blknr = __le32_to_cpu (indir1_block
                                       [fileblock - INDIRECT_BLOCKS]);
+#ifdef CFG_OPTIMIZE_EXT2_READ
+               while(((__le32_to_cpu (indir1_block[fileblock - INDIRECT_BLOCKS 
+ 1]) - \
+                       __le32_to_cpu (indir1_block[fileblock - 
INDIRECT_BLOCKS])) == 1) && \
+                       (fileblock < (blksz - 1))) {
+                       fileblock++;
+                       *stream += 1;
+               }
+#endif
        }
        /* Double indirect.  */
        else if (fileblock <
@@ -301,6 +349,9 @@ static int ext2fs_read_block (ext2fs_node_t node, int 
fileblock) {
                unsigned int perblock = blksz / 4;
                unsigned int rblock = fileblock - (INDIRECT_BLOCKS
                                                   + blksz / 4);
+#ifdef CFG_OPTIMIZE_EXT2_READ
+               int rbcnt = 0;
+#endif
 
                if (indir1_block == NULL) {
                        indir1_block = (uint32_t *) malloc (blksz);
@@ -370,6 +421,15 @@ static int ext2fs_read_block (ext2fs_node_t node, int 
fileblock) {
                                __le32_to_cpu (indir1_block[rblock / perblock]) 
<< log2_blksz;
                }
                blknr = __le32_to_cpu (indir2_block[rblock % perblock]);
+#ifdef CFG_OPTIMIZE_EXT2_READ
+               rbcnt = rblock % perblock;
+               while(((__le32_to_cpu (indir2_block[rbcnt + 1]) - \
+                       __le32_to_cpu (indir2_block[rbcnt])) == 1) \
+                       && (rbcnt < (blksz - 1))) {
+                       rbcnt++;
+                       *stream += 1;
+               }
+#endif
        }
        /* Tripple indirect.  */
        else {
@@ -382,7 +442,57 @@ static int ext2fs_read_block (ext2fs_node_t node, int 
fileblock) {
        return (blknr);
 }
 
+#ifdef CFG_OPTIMIZE_EXT2_READ
+int ext2fs_read_file
+       (ext2fs_node_t node, int pos, unsigned int len, char *buf) {
+       int log2blocksize = LOG2_EXT2_BLOCK_SIZE (node->data);
+       int blocksize = 1 << (log2blocksize + DISK_SECTOR_BITS);
+       unsigned int filesize = __le32_to_cpu(node->inode.size);
+       int blknr;
+       int blockend;
+       int status;
+       int remain = len;
+       char *buffer = buf;
+       int stream = 0;
+       int cur = pos / blocksize;
+       int blockoff = pos % blocksize;
+
+       /* Adjust len so it we can't read past the end of the file.  */
+       if (len > filesize) {
+               len = filesize;
+       }
 
+       while (remain > 0) {
+               blknr = ext2fs_read_block (node, cur, &stream);
+               if (blknr < 0) {
+                       return (-1);
+               }
+               blknr = blknr << log2blocksize; 
+       
+               if(remain < blocksize * stream) {
+                       blockend = remain;
+               } else {
+                       blockend = blocksize * stream;
+               }
+               
+               status = ext2fs_devread (blknr, blockoff, blockend, buffer);
+               if (status == 0) {
+                       return (-1);
+               }
+       
+               remain -= blockend;
+               buffer += blockend;
+               cur += stream;
+               blockoff = 0;
+       
+               if(remain == 0)
+                       return (len);
+               else if(remain < 0)
+                       return (-1);
+       }
+       return (len);
+}
+#else
 int ext2fs_read_file
        (ext2fs_node_t node, int pos, unsigned int len, char *buf) {
        int i;
@@ -442,6 +552,7 @@ int ext2fs_read_file
        }
        return (len);
 }
+#endif
 
 
 static int ext2fs_iterate_dir (ext2fs_node_t dir, char *name, ext2fs_node_t * 
fnode, int *ftype)
@@ -854,6 +965,16 @@ int ext2fs_mount (unsigned part_length) {
        if (__le16_to_cpu (data->sblock.magic) != EXT2_MAGIC) {
                goto fail;
        }
+#ifdef CFG_EXT2_SUPPORT_DYNAMIC_REV
+       debug("revision_level = 0x%x, inode_size = 0x%x\n", 
data->sblock.revision_level, \
+                       data->sblock.inode_size);
+       if (__le32_to_cpu (data->sblock.revision_level) == EXT2_GOOD_OLD_REV) {
+               ext2_inode_size = EXT2_GOOD_OLD_INODE_SIZE;
+       } else {
+               ext2_inode_size = __le16_to_cpu (data->sblock.inode_size);
+       }
+#endif
+       
        data->diropen.data = data;
        data->diropen.ino = 2;
        data->diropen.inode_read = 1;
-- 
1.6.0.rc1


Best Regards,
Ryan Chen


-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
_______________________________________________
U-Boot-Users mailing list
U-Boot-Users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/u-boot-users

Reply via email to