Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a86c6181 authored by Alex Tomas's avatar Alex Tomas Committed by Linus Torvalds
Browse files

[PATCH] ext3: add extent map support



On disk extents format:
/*
* this is extent on-disk structure
* it's used at the bottom of the tree
*/
struct ext3_extent {
__le32  ee_block;       /* first logical block extent covers */
__le16  ee_len;         /* number of blocks covered by extent */
__le16  ee_start_hi;    /* high 16 bits of physical block */
__le32  ee_start;       /* low 32 bigs of physical block */
};

Signed-off-by: default avatarAlex Tomas <alex@clusterfs.com>
Signed-off-by: default avatarDave Kleikamp <shaggy@austin.ibm.com>
Signed-off-by: default avatarAndrew Morton <akpm@osdl.org>
Signed-off-by: default avatarLinus Torvalds <torvalds@osdl.org>
parent c3fcc813
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -5,7 +5,7 @@
obj-$(CONFIG_EXT4DEV_FS) += ext4dev.o

ext4dev-y	:= balloc.o bitmap.o dir.o file.o fsync.o ialloc.o inode.o \
	   ioctl.o namei.o super.o symlink.o hash.o resize.o
	   ioctl.o namei.o super.o symlink.o hash.o resize.o extents.o

ext4dev-$(CONFIG_EXT4DEV_FS_XATTR)	+= xattr.o xattr_user.o xattr_trusted.o
ext4dev-$(CONFIG_EXT4DEV_FS_POSIX_ACL)	+= acl.o
+1 −2
Original line number Diff line number Diff line
@@ -134,8 +134,7 @@ static int ext4_readdir(struct file * filp,
		struct buffer_head *bh = NULL;

		map_bh.b_state = 0;
		err = ext4_get_blocks_handle(NULL, inode, blk, 1,
						&map_bh, 0, 0);
		err = ext4_get_blocks_wrap(NULL, inode, blk, 1, &map_bh, 0, 0);
		if (err > 0) {
			page_cache_readahead(sb->s_bdev->bd_inode->i_mapping,
				&filp->f_ra,

fs/ext4/extents.c

0 → 100644
+2075 −0

File added.

Preview size limit exceeded, changes collapsed.

+11 −0
Original line number Diff line number Diff line
@@ -615,6 +615,17 @@ struct inode *ext4_new_inode(handle_t *handle, struct inode * dir, int mode)
		ext4_std_error(sb, err);
		goto fail_free_drop;
	}
	if (test_opt(sb, EXTENTS)) {
		EXT4_I(inode)->i_flags |= EXT4_EXTENTS_FL;
		ext4_ext_tree_init(handle, inode);
		if (!EXT4_HAS_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_EXTENTS)) {
			err = ext4_journal_get_write_access(handle, EXT4_SB(sb)->s_sbh);
			if (err) goto fail;
			EXT4_SET_INCOMPAT_FEATURE(sb, EXT4_FEATURE_INCOMPAT_EXTENTS);
			BUFFER_TRACE(EXT4_SB(sb)->s_sbh, "call ext4_journal_dirty_metadata");
			err = ext4_journal_dirty_metadata(handle, EXT4_SB(sb)->s_sbh);
		}
	}

	ext4_debug("allocating inode %lu\n", inode->i_ino);
	goto really_out;
+11 −6
Original line number Diff line number Diff line
@@ -40,8 +40,6 @@
#include "xattr.h"
#include "acl.h"

static int ext4_writepage_trans_blocks(struct inode *inode);

/*
 * Test whether an inode is a fast symlink.
 */
@@ -804,6 +802,7 @@ int ext4_get_blocks_handle(handle_t *handle, struct inode *inode,
	ext4_fsblk_t first_block = 0;


	J_ASSERT(!(EXT4_I(inode)->i_flags & EXT4_EXTENTS_FL));
	J_ASSERT(handle != NULL || create == 0);
	depth = ext4_block_to_path(inode,iblock,offsets,&blocks_to_boundary);

@@ -984,7 +983,7 @@ static int ext4_get_block(struct inode *inode, sector_t iblock,

get_block:
	if (ret == 0) {
		ret = ext4_get_blocks_handle(handle, inode, iblock,
		ret = ext4_get_blocks_wrap(handle, inode, iblock,
					max_blocks, bh_result, create, 0);
		if (ret > 0) {
			bh_result->b_size = (ret << inode->i_blkbits);
@@ -1008,7 +1007,7 @@ struct buffer_head *ext4_getblk(handle_t *handle, struct inode *inode,
	dummy.b_state = 0;
	dummy.b_blocknr = -1000;
	buffer_trace_init(&dummy.b_history);
	err = ext4_get_blocks_handle(handle, inode, block, 1,
	err = ext4_get_blocks_wrap(handle, inode, block, 1,
					&dummy, create, 1);
	/*
	 * ext4_get_blocks_handle() returns number of blocks
@@ -1759,7 +1758,7 @@ void ext4_set_aops(struct inode *inode)
 * This required during truncate. We need to physically zero the tail end
 * of that block so it doesn't yield old data if the file is later grown.
 */
static int ext4_block_truncate_page(handle_t *handle, struct page *page,
int ext4_block_truncate_page(handle_t *handle, struct page *page,
		struct address_space *mapping, loff_t from)
{
	ext4_fsblk_t index = from >> PAGE_CACHE_SHIFT;
@@ -2263,6 +2262,9 @@ void ext4_truncate(struct inode *inode)
			return;
	}

	if (EXT4_I(inode)->i_flags & EXT4_EXTENTS_FL)
		return ext4_ext_truncate(inode, page);

	handle = start_transaction(inode);
	if (IS_ERR(handle)) {
		if (page) {
@@ -3003,12 +3005,15 @@ int ext4_setattr(struct dentry *dentry, struct iattr *attr)
 * block and work out the exact number of indirects which are touched.  Pah.
 */

static int ext4_writepage_trans_blocks(struct inode *inode)
int ext4_writepage_trans_blocks(struct inode *inode)
{
	int bpp = ext4_journal_blocks_per_page(inode);
	int indirects = (EXT4_NDIR_BLOCKS % bpp) ? 5 : 3;
	int ret;

	if (EXT4_I(inode)->i_flags & EXT4_EXTENTS_FL)
		return ext4_ext_writepage_trans_blocks(inode, bpp);

	if (ext4_should_journal_data(inode))
		ret = 3 * (bpp + indirects) + 2;
	else
Loading