summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorngkaho1234 <ngkaho1234@gmail.com>2015-12-28 13:05:04 +0000
committergkostka <kostka.grzegorz@gmail.com>2015-12-29 10:41:40 +0100
commit0c7f3604a3e2f26da99f8e126098ce8520139fbd (patch)
tree9e7a643d1e7e0954e662709133aca6297e9d143c
parentf3e06a2a6d91b4502fb0e0f70a79fb6daaf601e1 (diff)
Introduce initial support of ext3/4 journalling.
To achieve this, a glue layer between block cache and lwext4 core routines is added.
-rw-r--r--lwext4/ext4.c54
-rw-r--r--lwext4/ext4.h3
-rw-r--r--lwext4/ext4_balloc.c38
-rw-r--r--lwext4/ext4_bcache.c1
-rw-r--r--lwext4/ext4_bcache.h3
-rw-r--r--lwext4/ext4_blockdev.h4
-rw-r--r--lwext4/ext4_dir.c16
-rw-r--r--lwext4/ext4_dir_idx.c46
-rw-r--r--lwext4/ext4_extent.c30
-rw-r--r--lwext4/ext4_extent_full.c18
-rw-r--r--lwext4/ext4_fs.c46
-rw-r--r--lwext4/ext4_ialloc.c8
-rw-r--r--lwext4/ext4_trans.c115
-rw-r--r--lwext4/ext4_trans.h90
-rw-r--r--lwext4/ext4_xattr.c10
15 files changed, 356 insertions, 126 deletions
diff --git a/lwext4/ext4.c b/lwext4/ext4.c
index 2857fc6..8663001 100644
--- a/lwext4/ext4.c
+++ b/lwext4/ext4.c
@@ -251,7 +251,7 @@ static int ext4_link(struct ext4_mountpoint *mp, struct ext4_inode_ref *parent,
return EIO;
ext4_dir_en_set_inode(res.dentry, parent->index);
- ext4_bcache_set_dirty(res.block.buf);
+ ext4_trans_set_block_dirty(res.block.buf);
r = ext4_dir_destroy_result(ch, &res);
if (r != EOK)
return r;
@@ -414,6 +414,7 @@ int ext4_mount(const char *dev_name, const char *mount_point)
}
return r;
}
+ bd->fs = &mp->fs;
return r;
}
@@ -437,7 +438,7 @@ int ext4_umount(const char *mount_point)
r = ext4_fs_fini(&mp->fs);
if (r != EOK)
- return r;
+ goto Finish;
mp->mounted = 0;
@@ -446,8 +447,10 @@ int ext4_umount(const char *mount_point)
ext4_bcache_fini_dynamic(mp->fs.bdev->bc);
free(mp->fs.bdev->bc);
}
-
- return ext4_block_fini(mp->fs.bdev);
+ r = ext4_block_fini(mp->fs.bdev);
+Finish:
+ mp->fs.bdev->fs = NULL;
+ return r;
}
static struct ext4_mountpoint *ext4_get_mount(const char *path)
@@ -594,29 +597,6 @@ static void ext4_trans_abort(struct ext4_mountpoint *mp)
}
}
-int ext4_trans_get_write_access(struct ext4_fs *fs,
- struct ext4_block *block)
-{
- int r = EOK;
- if (fs->jbd_journal && fs->curr_trans) {
- struct jbd_journal *journal = fs->jbd_journal;
- struct jbd_trans *trans = fs->curr_trans;
- r = jbd_trans_get_access(journal, trans, block);
- }
- return r;
-}
-
-int ext4_trans_set_block_dirty(struct ext4_fs *fs,
- struct ext4_block *block)
-{
- int r = EOK;
- if (fs->jbd_journal && fs->curr_trans) {
- struct jbd_trans *trans = fs->curr_trans;
- r = jbd_trans_set_block_dirty(trans, block);
- }
- return r;
-}
-
int ext4_mount_point_stats(const char *mount_point,
struct ext4_mount_stats *stats)
{
@@ -2134,6 +2114,12 @@ int ext4_fsymlink(const char *target, const char *path)
Finish:
ext4_block_cache_write_back(mp->fs.bdev, 0);
+
+ if (r != EOK)
+ ext4_trans_abort(mp);
+ else
+ ext4_trans_stop(mp);
+
EXT4_MP_UNLOCK(mp);
return r;
}
@@ -2195,6 +2181,8 @@ int ext4_setxattr(const char *path, const char *name, size_t name_len,
return EINVAL;
EXT4_MP_LOCK(mp);
+ ext4_trans_start(mp);
+
r = ext4_generic_open2(&f, path, O_RDWR, EXT4_DE_UNKNOWN, NULL, NULL);
if (r != EOK)
goto Finish;
@@ -2217,6 +2205,11 @@ int ext4_setxattr(const char *path, const char *name, size_t name_len,
ext4_fs_put_xattr_ref(&xattr_ref);
ext4_fs_put_inode_ref(&inode_ref);
Finish:
+ if (r != EOK)
+ ext4_trans_abort(mp);
+ else
+ ext4_trans_stop(mp);
+
EXT4_MP_UNLOCK(mp);
return r;
}
@@ -2377,6 +2370,8 @@ int ext4_removexattr(const char *path, const char *name, size_t name_len)
return EINVAL;
EXT4_MP_LOCK(mp);
+ ext4_trans_start(mp);
+
r = ext4_generic_open2(&f, path, O_RDWR, EXT4_DE_UNKNOWN, NULL, NULL);
if (r != EOK)
goto Finish;
@@ -2399,6 +2394,11 @@ int ext4_removexattr(const char *path, const char *name, size_t name_len)
ext4_fs_put_xattr_ref(&xattr_ref);
ext4_fs_put_inode_ref(&inode_ref);
Finish:
+ if (r != EOK)
+ ext4_trans_abort(mp);
+ else
+ ext4_trans_stop(mp);
+
EXT4_MP_UNLOCK(mp);
return r;
diff --git a/lwext4/ext4.h b/lwext4/ext4.h
index 09abcbc..9679eb8 100644
--- a/lwext4/ext4.h
+++ b/lwext4/ext4.h
@@ -182,6 +182,9 @@ int ext4_mount(const char *dev_name, const char *mount_point);
* @return standard error code */
int ext4_umount(const char *mount_point);
+int ext4_journal_start(const char *mount_point);
+
+int ext4_journal_stop(const char *mount_point);
/**@brief Journal recovery.
* @param mount_point mount point
diff --git a/lwext4/ext4_balloc.c b/lwext4/ext4_balloc.c
index b840bea..8bba9f7 100644
--- a/lwext4/ext4_balloc.c
+++ b/lwext4/ext4_balloc.c
@@ -165,7 +165,7 @@ int ext4_balloc_free_block(struct ext4_inode_ref *inode_ref, ext4_fsblk_t baddr)
struct ext4_block bitmap_block;
- rc = ext4_block_get(fs->bdev, &bitmap_block, bitmap_block_addr);
+ rc = ext4_trans_block_get(fs->bdev, &bitmap_block, bitmap_block_addr);
if (rc != EOK) {
ext4_fs_put_block_group_ref(&bg_ref);
return rc;
@@ -181,7 +181,7 @@ int ext4_balloc_free_block(struct ext4_inode_ref *inode_ref, ext4_fsblk_t baddr)
/* Modify bitmap */
ext4_bmap_bit_clr(bitmap_block.data, index_in_group);
ext4_balloc_set_bitmap_csum(sb, bg, bitmap_block.data);
- ext4_bcache_set_dirty(bitmap_block.buf);
+ ext4_trans_set_block_dirty(bitmap_block.buf);
/* Release block with bitmap */
rc = ext4_block_set(fs->bdev, &bitmap_block);
@@ -211,6 +211,12 @@ int ext4_balloc_free_block(struct ext4_inode_ref *inode_ref, ext4_fsblk_t baddr)
bg_ref.dirty = true;
+ rc = ext4_trans_try_revoke_block(fs->bdev, baddr);
+ if (rc != EOK) {
+ bg_ref.dirty = false;
+ ext4_fs_put_block_group_ref(&bg_ref);
+ return rc;
+ }
ext4_bcache_invalidate_lba(fs->bdev->bc, baddr, 1);
/* Release block group reference */
return ext4_fs_put_block_group_ref(&bg_ref);
@@ -256,7 +262,7 @@ int ext4_balloc_free_blocks(struct ext4_inode_ref *inode_ref,
ext4_fsblk_t bitmap_blk = ext4_bg_get_block_bitmap(bg, sb);
struct ext4_block blk;
- rc = ext4_block_get(fs->bdev, &blk, bitmap_blk);
+ rc = ext4_trans_block_get(fs->bdev, &blk, bitmap_blk);
if (rc != EOK) {
ext4_fs_put_block_group_ref(&bg_ref);
return rc;
@@ -277,7 +283,7 @@ int ext4_balloc_free_blocks(struct ext4_inode_ref *inode_ref,
/* Modify bitmap */
ext4_bmap_bits_free(blk.data, idx_in_bg_first, free_cnt);
ext4_balloc_set_bitmap_csum(sb, bg, blk.data);
- ext4_bcache_set_dirty(blk.buf);
+ ext4_trans_set_block_dirty(blk.buf);
count -= free_cnt;
first += free_cnt;
@@ -318,6 +324,14 @@ int ext4_balloc_free_blocks(struct ext4_inode_ref *inode_ref,
bg_first++;
}
+ uint32_t i;
+ for (i = 0;i < count;i++) {
+ rc = ext4_trans_try_revoke_block(fs->bdev, first + i);
+ if (rc != EOK)
+ return rc;
+
+ }
+
ext4_bcache_invalidate_lba(fs->bdev->bc, first, count);
/*All blocks should be released*/
ext4_assert(count == 0);
@@ -368,7 +382,7 @@ int ext4_balloc_alloc_block(struct ext4_inode_ref *inode_ref,
/* Load block with bitmap */
bmp_blk_adr = ext4_bg_get_block_bitmap(bg_ref.block_group, sb);
- r = ext4_block_get(inode_ref->fs->bdev, &b, bmp_blk_adr);
+ r = ext4_trans_block_get(inode_ref->fs->bdev, &b, bmp_blk_adr);
if (r != EOK) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
@@ -386,7 +400,7 @@ int ext4_balloc_alloc_block(struct ext4_inode_ref *inode_ref,
ext4_bmap_bit_set(b.data, idx_in_bg);
ext4_balloc_set_bitmap_csum(sb, bg_ref.block_group,
b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
r = ext4_block_set(inode_ref->fs->bdev, &b);
if (r != EOK) {
ext4_fs_put_block_group_ref(&bg_ref);
@@ -410,7 +424,7 @@ int ext4_balloc_alloc_block(struct ext4_inode_ref *inode_ref,
ext4_bmap_bit_set(b.data, tmp_idx);
ext4_balloc_set_bitmap_csum(sb, bg, b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
r = ext4_block_set(inode_ref->fs->bdev, &b);
if (r != EOK)
return r;
@@ -425,7 +439,7 @@ int ext4_balloc_alloc_block(struct ext4_inode_ref *inode_ref,
if (r == EOK) {
ext4_bmap_bit_set(b.data, rel_blk_idx);
ext4_balloc_set_bitmap_csum(sb, bg_ref.block_group, b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
r = ext4_block_set(inode_ref->fs->bdev, &b);
if (r != EOK)
return r;
@@ -466,7 +480,7 @@ goal_failed:
/* Load block with bitmap */
bmp_blk_adr = ext4_bg_get_block_bitmap(bg, sb);
- r = ext4_block_get(inode_ref->fs->bdev, &b, bmp_blk_adr);
+ r = ext4_trans_block_get(inode_ref->fs->bdev, &b, bmp_blk_adr);
if (r != EOK) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
@@ -493,7 +507,7 @@ goal_failed:
if (r == EOK) {
ext4_bmap_bit_set(b.data, rel_blk_idx);
ext4_balloc_set_bitmap_csum(sb, bg, b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
r = ext4_block_set(inode_ref->fs->bdev, &b);
if (r != EOK) {
ext4_fs_put_block_group_ref(&bg_ref);
@@ -576,7 +590,7 @@ int ext4_balloc_try_alloc_block(struct ext4_inode_ref *inode_ref,
bmp_blk_addr = ext4_bg_get_block_bitmap(bg_ref.block_group, sb);
struct ext4_block b;
- rc = ext4_block_get(fs->bdev, &b, bmp_blk_addr);
+ rc = ext4_trans_block_get(fs->bdev, &b, bmp_blk_addr);
if (rc != EOK) {
ext4_fs_put_block_group_ref(&bg_ref);
return rc;
@@ -596,7 +610,7 @@ int ext4_balloc_try_alloc_block(struct ext4_inode_ref *inode_ref,
if (*free) {
ext4_bmap_bit_set(b.data, index_in_group);
ext4_balloc_set_bitmap_csum(sb, bg_ref.block_group, b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
}
/* Release block with bitmap */
diff --git a/lwext4/ext4_bcache.c b/lwext4/ext4_bcache.c
index 628735a..c1da95d 100644
--- a/lwext4/ext4_bcache.c
+++ b/lwext4/ext4_bcache.c
@@ -132,6 +132,7 @@ ext4_buf_alloc(struct ext4_bcache *bc, uint64_t lba)
buf->lba = lba;
buf->data = data;
+ buf->bc = bc;
return buf;
}
diff --git a/lwext4/ext4_bcache.h b/lwext4/ext4_bcache.h
index c83f1b9..ca606ad 100644
--- a/lwext4/ext4_bcache.h
+++ b/lwext4/ext4_bcache.h
@@ -85,6 +85,9 @@ struct ext4_buf {
/**@brief Reference count table*/
uint32_t refctr;
+ /**@brief The block cache this buffer belongs to. */
+ struct ext4_bcache *bc;
+
/**@brief Whether or not buffer is on dirty list.*/
bool on_dirty_list;
diff --git a/lwext4/ext4_blockdev.h b/lwext4/ext4_blockdev.h
index aeb348b..f5329ec 100644
--- a/lwext4/ext4_blockdev.h
+++ b/lwext4/ext4_blockdev.h
@@ -42,6 +42,7 @@ extern "C" {
#include "ext4_config.h"
#include "ext4_bcache.h"
+#include "ext4_trans.h"
#include "ext4_debug.h"
#include <stdbool.h>
@@ -122,6 +123,9 @@ struct ext4_blockdev {
/**@brief Cache write back mode reference counter*/
uint32_t cache_write_back;
+
+ /**@brief The filesystem this block device belongs to. */
+ struct ext4_fs *fs;
};
/**@brief Static initialization of the block device.*/
diff --git a/lwext4/ext4_dir.c b/lwext4/ext4_dir.c
index b22e88b..62909e4 100644
--- a/lwext4/ext4_dir.c
+++ b/lwext4/ext4_dir.c
@@ -239,7 +239,7 @@ static int ext4_dir_iterator_seek(struct ext4_dir_iter *it, uint64_t pos)
if (r != EOK)
return r;
- r = ext4_block_get(bdev, &it->curr_blk, next_blk);
+ r = ext4_trans_block_get(bdev, &it->curr_blk, next_blk);
if (r != EOK) {
it->curr_blk.lb_id = 0;
return r;
@@ -364,7 +364,7 @@ int ext4_dir_add_entry(struct ext4_inode_ref *parent, const char *name,
return r;
struct ext4_block block;
- r = ext4_block_get(fs->bdev, &block, fblock);
+ r = ext4_trans_block_get(fs->bdev, &block, fblock);
if (r != EOK)
return r;
@@ -402,7 +402,7 @@ int ext4_dir_add_entry(struct ext4_inode_ref *parent, const char *name,
/* Load new block */
struct ext4_block b;
- r = ext4_block_get_noread(fs->bdev, &b, fblock);
+ r = ext4_trans_block_get_noread(fs->bdev, &b, fblock);
if (r != EOK)
return r;
@@ -421,7 +421,7 @@ int ext4_dir_add_entry(struct ext4_inode_ref *parent, const char *name,
}
ext4_dir_set_csum(parent, (void *)b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
r = ext4_block_set(fs->bdev, &b);
return r;
@@ -474,7 +474,7 @@ int ext4_dir_find_entry(struct ext4_dir_search_result *result,
/* Load data block */
struct ext4_block b;
- r = ext4_block_get(parent->fs->bdev, &b, fblock);
+ r = ext4_trans_block_get(parent->fs->bdev, &b, fblock);
if (r != EOK)
return r;
@@ -554,7 +554,7 @@ int ext4_dir_remove_entry(struct ext4_inode_ref *parent, const char *name,
ext4_dir_set_csum(parent,
(struct ext4_dir_en *)result.block.data);
- ext4_bcache_set_dirty(result.block.buf);
+ ext4_trans_set_block_dirty(result.block.buf);
return ext4_dir_destroy_result(parent, &result);
}
@@ -591,7 +591,7 @@ int ext4_dir_try_insert_entry(struct ext4_sblock *sb,
ext4_dir_write_entry(sb, start, rec_len, child, name,
name_len);
ext4_dir_set_csum(inode_ref, (void *)dst_blk->data);
- ext4_bcache_set_dirty(dst_blk->buf);
+ ext4_trans_set_block_dirty(dst_blk->buf);
return EOK;
}
@@ -620,7 +620,7 @@ int ext4_dir_try_insert_entry(struct ext4_sblock *sb,
ext4_dir_set_csum(inode_ref,
(void *)dst_blk->data);
- ext4_bcache_set_dirty(dst_blk->buf);
+ ext4_trans_set_block_dirty(dst_blk->buf);
return EOK;
}
}
diff --git a/lwext4/ext4_dir_idx.c b/lwext4/ext4_dir_idx.c
index 1b78905..28ec00c 100644
--- a/lwext4/ext4_dir_idx.c
+++ b/lwext4/ext4_dir_idx.c
@@ -353,7 +353,7 @@ int ext4_dir_dx_init(struct ext4_inode_ref *dir, struct ext4_inode_ref *parent)
return rc;
struct ext4_block block;
- rc = ext4_block_get_noread(dir->fs->bdev, &block, fblock);
+ rc = ext4_trans_block_get_noread(dir->fs->bdev, &block, fblock);
if (rc != EOK)
return rc;
@@ -403,7 +403,7 @@ int ext4_dir_dx_init(struct ext4_inode_ref *dir, struct ext4_inode_ref *parent)
}
struct ext4_block new_block;
- rc = ext4_block_get_noread(dir->fs->bdev, &new_block, fblock);
+ rc = ext4_trans_block_get_noread(dir->fs->bdev, &new_block, fblock);
if (rc != EOK) {
ext4_block_set(dir->fs->bdev, &block);
return rc;
@@ -425,7 +425,7 @@ int ext4_dir_dx_init(struct ext4_inode_ref *dir, struct ext4_inode_ref *parent)
ext4_dir_en_set_inode(be, 0);
- ext4_bcache_set_dirty(new_block.buf);
+ ext4_trans_set_block_dirty(new_block.buf);
rc = ext4_block_set(dir->fs->bdev, &new_block);
if (rc != EOK) {
ext4_block_set(dir->fs->bdev, &block);
@@ -437,7 +437,7 @@ int ext4_dir_dx_init(struct ext4_inode_ref *dir, struct ext4_inode_ref *parent)
ext4_dir_dx_entry_set_block(entry, iblock);
ext4_dir_set_dx_csum(dir, (struct ext4_dir_en *)block.data);
- ext4_bcache_set_dirty(block.buf);
+ ext4_trans_set_block_dirty(block.buf);
return ext4_block_set(dir->fs->bdev, &block);
}
@@ -580,7 +580,7 @@ static int ext4_dir_dx_get_leaf(struct ext4_hash_info *hinfo,
if (r != EOK)
return r;
- r = ext4_block_get(inode_ref->fs->bdev, tmp_blk, fblk);
+ r = ext4_trans_block_get(inode_ref->fs->bdev, tmp_blk, fblk);
if (r != EOK)
return r;
@@ -662,7 +662,7 @@ static int ext4_dir_dx_next_block(struct ext4_inode_ref *inode_ref,
return r;
struct ext4_block b;
- r = ext4_block_get(inode_ref->fs->bdev, &b, blk_adr);
+ r = ext4_trans_block_get(inode_ref->fs->bdev, &b, blk_adr);
if (r != EOK)
return r;
@@ -705,7 +705,7 @@ int ext4_dir_dx_find_entry(struct ext4_dir_search_result *result,
struct ext4_fs *fs = inode_ref->fs;
struct ext4_block root_block;
- rc = ext4_block_get(fs->bdev, &root_block, root_block_addr);
+ rc = ext4_trans_block_get(fs->bdev, &root_block, root_block_addr);
if (rc != EOK)
return rc;
@@ -753,7 +753,7 @@ int ext4_dir_dx_find_entry(struct ext4_dir_search_result *result,
if (rc != EOK)
goto cleanup;
- rc = ext4_block_get(fs->bdev, &b, leaf_block_addr);
+ rc = ext4_trans_block_get(fs->bdev, &b, leaf_block_addr);
if (rc != EOK)
goto cleanup;
@@ -897,7 +897,7 @@ ext4_dir_dx_insert_entry(struct ext4_inode_ref *inode_ref __unused,
ext4_dir_dx_entry_set_hash(new_index_entry, hash);
ext4_dir_dx_climit_set_count(climit, count + 1);
ext4_dir_set_dx_csum(inode_ref, (void *)index_block->b.data);
- ext4_bcache_set_dirty(index_block->b.buf);
+ ext4_trans_set_block_dirty(index_block->b.buf);
}
/**@brief Split directory entries to two parts preventing node overflow.
@@ -994,7 +994,7 @@ static int ext4_dir_dx_split_data(struct ext4_inode_ref *inode_ref,
/* Load new block */
struct ext4_block new_data_block_tmp;
- rc = ext4_block_get_noread(inode_ref->fs->bdev, &new_data_block_tmp,
+ rc = ext4_trans_block_get_noread(inode_ref->fs->bdev, &new_data_block_tmp,
new_fblock);
if (rc != EOK) {
free(sort);
@@ -1073,8 +1073,8 @@ static int ext4_dir_dx_split_data(struct ext4_inode_ref *inode_ref,
}
ext4_dir_set_csum(inode_ref, (void *)old_data_block->data);
ext4_dir_set_csum(inode_ref, (void *)new_data_block_tmp.data);
- ext4_bcache_set_dirty(old_data_block->buf);
- ext4_bcache_set_dirty(new_data_block_tmp.buf);
+ ext4_trans_set_block_dirty(old_data_block->buf);
+ ext4_trans_set_block_dirty(new_data_block_tmp.buf);
free(sort);
free(entry_buffer);
@@ -1142,7 +1142,7 @@ ext4_dir_dx_split_index(struct ext4_inode_ref *ino_ref,
/* load new block */
struct ext4_block b;
- r = ext4_block_get_noread(ino_ref->fs->bdev, &b, new_fblk);
+ r = ext4_trans_block_get_noread(ino_ref->fs->bdev, &b, new_fblk);
if (r != EOK)
return r;
@@ -1187,7 +1187,7 @@ ext4_dir_dx_split_index(struct ext4_inode_ref *ino_ref,
ino_ref,
(struct ext4_dir_en *)
dxb->b.data);
- ext4_bcache_set_dirty(dxb->b.buf);
+ ext4_trans_set_block_dirty(dxb->b.buf);
struct ext4_block block_tmp = dxb->b;
@@ -1205,11 +1205,11 @@ ext4_dir_dx_split_index(struct ext4_inode_ref *ino_ref,
new_iblk);
ext4_dir_set_dx_csum(ino_ref, (void*)dx_blks[0].b.data);
ext4_dir_set_dx_csum(ino_ref, (void*)dx_blks[1].b.data);
- ext4_bcache_set_dirty(dx_blks[0].b.buf);
- ext4_bcache_set_dirty(dx_blks[1].b.buf);
+ ext4_trans_set_block_dirty(dx_blks[0].b.buf);
+ ext4_trans_set_block_dirty(dx_blks[1].b.buf);
ext4_dir_set_dx_csum(ino_ref, (void *)b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
return ext4_block_set(ino_ref->fs->bdev, &b);
} else {
size_t sz;
@@ -1241,8 +1241,8 @@ ext4_dir_dx_split_index(struct ext4_inode_ref *ino_ref,
ext4_dir_set_dx_csum(ino_ref, (void*)dx_blks[0].b.data);
ext4_dir_set_dx_csum(ino_ref, (void*)dx_blks[1].b.data);
- ext4_bcache_set_dirty(dx_blks[0].b.buf);
- ext4_bcache_set_dirty(dx_blks[1].b.buf);
+ ext4_trans_set_block_dirty(dx_blks[0].b.buf);
+ ext4_trans_set_block_dirty(dx_blks[1].b.buf);
}
}
@@ -1263,7 +1263,7 @@ int ext4_dir_dx_add_entry(struct ext4_inode_ref *parent,
struct ext4_fs *fs = parent->fs;
struct ext4_block root_blk;
- r = ext4_block_get(fs->bdev, &root_blk, rblock_addr);
+ r = ext4_trans_block_get(fs->bdev, &root_blk, rblock_addr);
if (r != EOK)
return r;
@@ -1316,7 +1316,7 @@ int ext4_dir_dx_add_entry(struct ext4_inode_ref *parent,
goto release_target_index;
struct ext4_block target_block;
- r = ext4_block_get(fs->bdev, &target_block, leaf_block_addr);
+ r = ext4_trans_block_get(fs->bdev, &target_block, leaf_block_addr);
if (r != EOK)
goto release_index;
@@ -1394,7 +1394,7 @@ int ext4_dir_dx_reset_parent_inode(struct ext4_inode_ref *dir,
return rc;
struct ext4_block block;
- rc = ext4_block_get(dir->fs->bdev, &block, fblock);
+ rc = ext4_trans_block_get(dir->fs->bdev, &block, fblock);
if (rc != EOK)
return rc;
@@ -1414,7 +1414,7 @@ int ext4_dir_dx_reset_parent_inode(struct ext4_inode_ref *dir,
ext4_dx_dot_en_set_inode(&root->dots[1], parent_inode);
ext4_dir_set_dx_csum(dir, (void *)block.data);
- ext4_bcache_set_dirty(block.buf);
+ ext4_trans_set_block_dirty(block.buf);
return ext4_block_set(dir->fs->bdev, &block);
}
diff --git a/lwext4/ext4_extent.c b/lwext4/ext4_extent.c
index d6f373b..831cb48 100644
--- a/lwext4/ext4_extent.c
+++ b/lwext4/ext4_extent.c
@@ -257,7 +257,7 @@ ext4_extent_find_block(struct ext4_inode_ref *inode_ref, uint32_t iblock,
return rc;
}
- int rc = ext4_block_get(inode_ref->fs->bdev, &block, child);
+ int rc = ext4_trans_block_get(inode_ref->fs->bdev, &block, child);
if (rc != EOK)
return rc;
if (!ext4_extent_verify_block_csum(inode_ref,
@@ -342,7 +342,7 @@ static int ext4_extent_find_extent(struct ext4_inode_ref *inode_ref,
ext4_extent_index_get_leaf(tmp_path[pos].index);
struct ext4_block block;
- rc = ext4_block_get(inode_ref->fs->bdev, &block, fblock);
+ rc = ext4_trans_block_get(inode_ref->fs->bdev, &block, fblock);
if (rc != EOK)
goto cleanup;
@@ -419,7 +419,7 @@ static int ext4_extent_release_branch(struct ext4_inode_ref *inode_ref,
ext4_fsblk_t fblock = ext4_extent_index_get_leaf(index);
uint32_t i;
struct ext4_block block;
- int rc = ext4_block_get(inode_ref->fs->bdev, &block, fblock);
+ int rc = ext4_trans_block_get(inode_ref->fs->bdev, &block, fblock);
if (rc != EOK)
return rc;
@@ -534,7 +534,7 @@ int ext4_extent_remove_space(struct ext4_inode_ref *inode_ref, ext4_lblk_t from,
ext4_extent_header_set_entries_count(path_ptr->header, entries);
ext4_extent_block_csum_set(inode_ref, path_ptr->header);
- ext4_bcache_set_dirty(path_ptr->block.buf);
+ ext4_trans_set_block_dirty(path_ptr->block.buf);
/* If leaf node is empty, parent entry must be modified */
bool remove_parent_record = false;
@@ -576,7 +576,7 @@ int ext4_extent_remove_space(struct ext4_inode_ref *inode_ref, ext4_lblk_t from,
ext4_extent_header_set_entries_count(path_ptr->header, entries);
ext4_extent_block_csum_set(inode_ref, path_ptr->header);
- ext4_bcache_set_dirty(path_ptr->block.buf);
+ ext4_trans_set_block_dirty(path_ptr->block.buf);
/* Free the node if it is empty */
if ((entries == 0) && (path_ptr != path)) {
@@ -651,7 +651,7 @@ static int ext4_extent_append_extent(struct ext4_inode_ref *inode_ref,
struct ext4_block block;
rc =
- ext4_block_get_noread(inode_ref->fs->bdev, &block, fblock);
+ ext4_trans_block_get_noread(inode_ref->fs->bdev, &block, fblock);
if (rc != EOK) {
ext4_balloc_free_block(inode_ref, fblock);
return rc;
@@ -704,7 +704,7 @@ static int ext4_extent_append_extent(struct ext4_inode_ref *inode_ref,
ext4_extent_header_set_generation(path_ptr->header, 0);
ext4_extent_block_csum_set(inode_ref, path_ptr->header);
- ext4_bcache_set_dirty(path_ptr->block.buf);
+ ext4_trans_set_block_dirty(path_ptr->block.buf);
/* Jump to the preceding item */
path_ptr--;
@@ -730,7 +730,7 @@ static int ext4_extent_append_extent(struct ext4_inode_ref *inode_ref,
ext4_extent_header_set_entries_count(path_ptr->header,
entries + 1);
ext4_extent_block_csum_set(inode_ref, path_ptr->header);
- ext4_bcache_set_dirty(path_ptr->block.buf);
+ ext4_trans_set_block_dirty(path_ptr->block.buf);
/* No more splitting needed */
return EOK;
@@ -755,7 +755,7 @@ static int ext4_extent_append_extent(struct ext4_inode_ref *inode_ref,
return rc;
struct ext4_block block;
- rc = ext4_block_get_noread(inode_ref->fs->bdev, &block, new_fblock);
+ rc = ext4_trans_block_get_noread(inode_ref->fs->bdev, &block, new_fblock);
if (rc != EOK)
return rc;
@@ -813,7 +813,7 @@ static int ext4_extent_append_extent(struct ext4_inode_ref *inode_ref,
limit);
ext4_extent_block_csum_set(inode_ref, old_root->header);
- ext4_bcache_set_dirty(old_root->block.buf);
+ ext4_trans_set_block_dirty(old_root->block.buf);
/* Re-initialize new root metadata */
new_root->depth = root_depth + 1;
@@ -831,7 +831,7 @@ static int ext4_extent_append_extent(struct ext4_inode_ref *inode_ref,
/* Since new_root belongs to on-disk inode,
* we don't do checksum here */
- ext4_bcache_set_dirty(new_root->block.buf);
+ ext4_trans_set_block_dirty(new_root->block.buf);
} else {
if (path->depth) {
path->index =
@@ -848,7 +848,7 @@ static int ext4_extent_append_extent(struct ext4_inode_ref *inode_ref,
ext4_extent_header_set_entries_count(path->header, entries + 1);
/* Since new_root belongs to on-disk inode,
* we don't do checksum here */
- ext4_bcache_set_dirty(path->block.buf);
+ ext4_trans_set_block_dirty(path->block.buf);
}
return EOK;
@@ -928,7 +928,7 @@ ext4_extent_append_block(struct ext4_inode_ref *inode_ref, uint32_t *iblock,
}
ext4_extent_block_csum_set(inode_ref, path_ptr->header);
- ext4_bcache_set_dirty(path_ptr->block.buf);
+ ext4_trans_set_block_dirty(path_ptr->block.buf);
goto finish;
} else {
@@ -970,7 +970,7 @@ ext4_extent_append_block(struct ext4_inode_ref *inode_ref, uint32_t *iblock,
}
ext4_extent_block_csum_set(inode_ref, path_ptr->header);
- ext4_bcache_set_dirty(path_ptr->block.buf);
+ ext4_trans_set_block_dirty(path_ptr->block.buf);
goto finish;
}
@@ -1011,7 +1011,7 @@ append_extent:
}
ext4_extent_block_csum_set(inode_ref, path_ptr->header);
- ext4_bcache_set_dirty(path_ptr->block.buf);
+ ext4_trans_set_block_dirty(path_ptr->block.buf);
finish:
/* Set return values */
diff --git a/lwext4/ext4_extent_full.c b/lwext4/ext4_extent_full.c
index 2d34d67..3bc1836 100644
--- a/lwext4/ext4_extent_full.c
+++ b/lwext4/ext4_extent_full.c
@@ -353,7 +353,7 @@ static int ext4_ext_dirty(struct ext4_inode_ref *inode_ref,
struct ext4_extent_path *path)
{
if (path->block.lb_id)
- ext4_bcache_set_dirty(path->block.buf);
+ ext4_trans_set_block_dirty(path->block.buf);
else
inode_ref->dirty = true;
@@ -440,7 +440,7 @@ static int read_extent_tree_block(struct ext4_inode_ref *inode_ref,
{
int err;
- err = ext4_block_get(inode_ref->fs->bdev, bh, pblk);
+ err = ext4_trans_block_get(inode_ref->fs->bdev, bh, pblk);
if (err != EOK)
goto errout;
@@ -627,7 +627,7 @@ static int ext4_ext_split_node(struct ext4_inode_ref *inode_ref,
goto cleanup;
/* For write access.# */
- ret = ext4_block_get_noread(inode_ref->fs->bdev, &bh, newblock);
+ ret = ext4_trans_block_get_noread(inode_ref->fs->bdev, &bh, newblock);
if (ret != EOK)
goto cleanup;
@@ -798,7 +798,7 @@ out:
} else if (bh.lb_id) {
/* If we got a sibling leaf. */
ext4_extent_block_csum_set(inode_ref, ext_block_hdr(&bh));
- ext4_bcache_set_dirty(bh.buf);
+ ext4_trans_set_block_dirty(bh.buf);
spt->path.p_block = ext4_idx_pblock(ix);
spt->path.depth = to_le16(eh->depth);
@@ -1070,7 +1070,7 @@ out:
} else if (bh.lb_id) {
/* If we got a sibling leaf. */
ext4_extent_block_csum_set(inode_ref, ext_block_hdr(&bh));
- ext4_bcache_set_dirty(bh.buf);
+ ext4_trans_set_block_dirty(bh.buf);
spt->path.p_block = ext4_ext_pblock(ex);
spt->path.depth = to_le16(eh->depth);
@@ -1129,7 +1129,7 @@ static int ext4_ext_grow_indepth(struct ext4_inode_ref *inode_ref,
return err;
/* # */
- err = ext4_block_get_noread(inode_ref->fs->bdev, &bh, newblock);
+ err = ext4_trans_block_get_noread(inode_ref->fs->bdev, &bh, newblock);
if (err != EOK) {
ext4_ext_free_blocks(inode_ref, newblock, 1, 0);
return err;
@@ -1166,7 +1166,7 @@ static int ext4_ext_grow_indepth(struct ext4_inode_ref *inode_ref,
}
neh->depth = to_le16(to_le16(neh->depth) + 1);
- ext4_bcache_set_dirty(bh.buf);
+ ext4_trans_set_block_dirty(bh.buf);
inode_ref->dirty = true;
ext4_block_set(inode_ref->fs->bdev, &bh);
@@ -1723,12 +1723,12 @@ static int ext4_ext_zero_unwritten_range(struct ext4_inode_ref *inode_ref,
uint32_t block_size = ext4_sb_get_block_size(&inode_ref->fs->sb);
for (i = 0; i < blocks_count; i++) {
struct ext4_block bh = EXT4_BLOCK_ZERO();
- err = ext4_block_get_noread(inode_ref->fs->bdev, &bh, block + i);
+ err = ext4_trans_block_get_noread(inode_ref->fs->bdev, &bh, block + i);
if (err != EOK)
break;
memset(bh.data, 0, block_size);
- ext4_bcache_set_dirty(bh.buf);
+ ext4_trans_set_block_dirty(bh.buf);
err = ext4_block_set(inode_ref->fs->bdev, &bh);
if (err != EOK)
break;
diff --git a/lwext4/ext4_fs.c b/lwext4/ext4_fs.c
index 7250839..f76cda8 100644
--- a/lwext4/ext4_fs.c
+++ b/lwext4/ext4_fs.c
@@ -302,7 +302,7 @@ static int ext4_fs_init_block_bitmap(struct ext4_block_group_ref *bg_ref)
uint32_t inode_table_bcnt = inodes_per_group * inode_size / block_size;
struct ext4_block block_bitmap;
- rc = ext4_block_get_noread(bg_ref->fs->bdev, &block_bitmap, bmp_blk);
+ rc = ext4_trans_block_get_noread(bg_ref->fs->bdev, &block_bitmap, bmp_blk);
if (rc != EOK)
return rc;
@@ -356,7 +356,7 @@ static int ext4_fs_init_block_bitmap(struct ext4_block_group_ref *bg_ref)
* of bitmap ), set rest of the block bitmap to 1
*/
ext4_fs_mark_bitmap_end(group_blocks, block_size * 8, block_bitmap.data);
- ext4_bcache_set_dirty(block_bitmap.buf);
+ ext4_trans_set_block_dirty(block_bitmap.buf);
ext4_balloc_set_bitmap_csum(sb, bg_ref->block_group, block_bitmap.data);
bg_ref->dirty = true;
@@ -379,7 +379,7 @@ static int ext4_fs_init_inode_bitmap(struct ext4_block_group_ref *bg_ref)
ext4_fsblk_t bitmap_block_addr = ext4_bg_get_inode_bitmap(bg, sb);
struct ext4_block b;
- rc = ext4_block_get_noread(bg_ref->fs->bdev, &b, bitmap_block_addr);
+ rc = ext4_trans_block_get_noread(bg_ref->fs->bdev, &b, bitmap_block_addr);
if (rc != EOK)
return rc;
@@ -399,7 +399,7 @@ static int ext4_fs_init_inode_bitmap(struct ext4_block_group_ref *bg_ref)
if (i < end_bit)
memset(b.data + (i >> 3), 0xff, (end_bit - i) >> 3);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
ext4_ialloc_set_bitmap_csum(sb, bg, b.data);
bg_ref->dirty = true;
@@ -435,12 +435,12 @@ static int ext4_fs_init_inode_table(struct ext4_block_group_ref *bg_ref)
/* Initialization of all itable blocks */
for (fblock = first_block; fblock <= last_block; ++fblock) {
struct ext4_block b;
- int rc = ext4_block_get_noread(bg_ref->fs->bdev, &b, fblock);
+ int rc = ext4_trans_block_get_noread(bg_ref->fs->bdev, &b, fblock);
if (rc != EOK)
return rc;
memset(b.data, 0, block_size);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
ext4_block_set(bg_ref->fs->bdev, &b);
if (rc != EOK)
@@ -566,7 +566,7 @@ int ext4_fs_get_block_group_ref(struct ext4_fs *fs, uint32_t bgid,
uint32_t offset = (bgid % dsc_cnt) * ext4_sb_get_desc_size(&fs->sb);
- int rc = ext4_block_get(fs->bdev, &ref->block, block_id);
+ int rc = ext4_trans_block_get(fs->bdev, &ref->block, block_id);
if (rc != EOK)
return rc;
@@ -629,7 +629,7 @@ int ext4_fs_put_block_group_ref(struct ext4_block_group_ref *ref)
ref->block_group->checksum = to_le16(cs);
/* Mark block dirty for writing changes to physical device */
- ext4_bcache_set_dirty(ref->block.buf);
+ ext4_trans_set_block_dirty(ref->block.buf);
}
/* Put back block, that contains block group descriptor */
@@ -745,7 +745,7 @@ __ext4_fs_get_inode_ref(struct ext4_fs *fs, uint32_t index,
ext4_fsblk_t block_id =
inode_table_start + (byte_offset_in_group / block_size);
- rc = ext4_block_get(fs->bdev, &ref->block, block_id);
+ rc = ext4_trans_block_get(fs->bdev, &ref->block, block_id);
if (rc != EOK) {
return rc;
}
@@ -781,7 +781,7 @@ int ext4_fs_put_inode_ref(struct ext4_inode_ref *ref)
if (ref->dirty) {
/* Mark block dirty for writing changes to physical device */
ext4_fs_set_inode_checksum(ref);
- ext4_bcache_set_dirty(ref->block.buf);
+ ext4_trans_set_block_dirty(ref->block.buf);
}
/* Put back block, that contains i-node */
@@ -937,7 +937,7 @@ int ext4_fs_free_inode(struct ext4_inode_ref *inode_ref)
/* 2) Double indirect */
fblock = ext4_inode_get_indirect_block(inode_ref->inode, 1);
if (fblock != 0) {
- int rc = ext4_block_get(fs->bdev, &block, fblock);
+ int rc = ext4_trans_block_get(fs->bdev, &block, fblock);
if (rc != EOK)
return rc;
@@ -968,7 +968,7 @@ int ext4_fs_free_inode(struct ext4_inode_ref *inode_ref)
fblock = ext4_inode_get_indirect_block(inode_ref->inode, 2);
if (fblock == 0)
goto finish;
- rc = ext4_block_get(fs->bdev, &block, fblock);
+ rc = ext4_trans_block_get(fs->bdev, &block, fblock);
if (rc != EOK)
return rc;
@@ -978,7 +978,7 @@ int ext4_fs_free_inode(struct ext4_inode_ref *inode_ref)
if (ind_block == 0)
continue;
- rc = ext4_block_get(fs->bdev, &subblock,
+ rc = ext4_trans_block_get(fs->bdev, &subblock,
ind_block);
if (rc != EOK) {
ext4_block_set(fs->bdev, &block);
@@ -1108,7 +1108,7 @@ static int ext4_fs_release_inode_block(struct ext4_inode_ref *inode_ref,
if (current_block == 0)
return EOK;
- int rc = ext4_block_get(fs->bdev, &block, current_block);
+ int rc = ext4_trans_block_get(fs->bdev, &block, current_block);
if (rc != EOK)
return rc;
@@ -1118,7 +1118,7 @@ static int ext4_fs_release_inode_block(struct ext4_inode_ref *inode_ref,
/* Set zero if physical data block address found */
if (level == 1) {
((uint32_t *)block.data)[offset_in_block] = to_le32(0);
- ext4_bcache_set_dirty(block.buf);
+ ext4_trans_set_block_dirty(block.buf);
}
rc = ext4_block_set(fs->bdev, &block);
@@ -1380,7 +1380,7 @@ static int ext4_fs_get_inode_dblk_idx_internal(struct ext4_inode_ref *inode_ref,
*/
while (l > 0) {
/* Load indirect block */
- int rc = ext4_block_get(fs->bdev, &block, current_block);
+ int rc = ext4_trans_block_get(fs->bdev, &block, current_block);
if (rc != EOK)
return rc;
@@ -1499,7 +1499,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
inode_ref->dirty = true;
/* Load newly allocated block */
- rc = ext4_block_get_noread(fs->bdev, &new_block, new_blk);
+ rc = ext4_trans_block_get_noread(fs->bdev, &new_block, new_blk);
if (rc != EOK) {
ext4_balloc_free_block(inode_ref, new_blk);
return rc;
@@ -1507,7 +1507,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
/* Initialize new block */
memset(new_block.data, 0, block_size);
- ext4_bcache_set_dirty(new_block.buf);
+ ext4_trans_set_block_dirty(new_block.buf);
/* Put back the allocated block */
rc = ext4_block_set(fs->bdev, &new_block);
@@ -1522,7 +1522,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
* or find null reference meaning we are dealing with sparse file
*/
while (l > 0) {
- int rc = ext4_block_get(fs->bdev, &block, current_block);
+ int rc = ext4_trans_block_get(fs->bdev, &block, current_block);
if (rc != EOK)
return rc;
@@ -1544,7 +1544,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
}
/* Load newly allocated block */
- rc = ext4_block_get_noread(fs->bdev, &new_block,
+ rc = ext4_trans_block_get_noread(fs->bdev, &new_block,
new_blk);
if (rc != EOK) {
@@ -1554,7 +1554,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
/* Initialize allocated block */
memset(new_block.data, 0, block_size);
- ext4_bcache_set_dirty(new_block.buf);
+ ext4_trans_set_block_dirty(new_block.buf);
rc = ext4_block_set(fs->bdev, &new_block);
if (rc != EOK) {
@@ -1565,7 +1565,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
/* Write block address to the parent */
uint32_t * p = (uint32_t * )block.data;
p[off_in_blk] = to_le32((uint32_t)new_blk);
- ext4_bcache_set_dirty(block.buf);
+ ext4_trans_set_block_dirty(block.buf);
current_block = new_blk;
}
@@ -1573,7 +1573,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
if (l == 1) {
uint32_t * p = (uint32_t * )block.data;
p[off_in_blk] = to_le32((uint32_t)fblock);
- ext4_bcache_set_dirty(block.buf);
+ ext4_trans_set_block_dirty(block.buf);
}
rc = ext4_block_set(fs->bdev, &block);
diff --git a/lwext4/ext4_ialloc.c b/lwext4/ext4_ialloc.c
index 7dad65d..a612a75 100644
--- a/lwext4/ext4_ialloc.c
+++ b/lwext4/ext4_ialloc.c
@@ -169,7 +169,7 @@ int ext4_ialloc_free_inode(struct ext4_fs *fs, uint32_t index, bool is_dir)
ext4_bg_get_inode_bitmap(bg, sb);
struct ext4_block b;
- rc = ext4_block_get(fs->bdev, &b, bitmap_block_addr);
+ rc = ext4_trans_block_get(fs->bdev, &b, bitmap_block_addr);
if (rc != EOK)
return rc;
@@ -184,7 +184,7 @@ int ext4_ialloc_free_inode(struct ext4_fs *fs, uint32_t index, bool is_dir)
uint32_t index_in_group = ext4_ialloc_inode_to_bgidx(sb, index);
ext4_bmap_bit_clr(b.data, index_in_group);
ext4_ialloc_set_bitmap_csum(sb, bg, b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
/* Put back the block with bitmap */
rc = ext4_block_set(fs->bdev, &b);
@@ -260,7 +260,7 @@ int ext4_ialloc_alloc_inode(struct ext4_fs *fs, uint32_t *idx, bool is_dir)
uint32_t bmp_blk_add = ext4_bg_get_inode_bitmap(bg, sb);
struct ext4_block b;
- rc = ext4_block_get(fs->bdev, &b, bmp_blk_add);
+ rc = ext4_trans_block_get(fs->bdev, &b, bmp_blk_add);
if (rc != EOK) {
ext4_fs_put_block_group_ref(&bg_ref);
return rc;
@@ -300,7 +300,7 @@ int ext4_ialloc_alloc_inode(struct ext4_fs *fs, uint32_t *idx, bool is_dir)
/* Free i-node found, save the bitmap */
ext4_ialloc_set_bitmap_csum(sb,bg,
b.data);
- ext4_bcache_set_dirty(b.buf);
+ ext4_trans_set_block_dirty(b.buf);
ext4_block_set(fs->bdev, &b);
if (rc != EOK) {
diff --git a/lwext4/ext4_trans.c b/lwext4/ext4_trans.c
new file mode 100644
index 0000000..1aa8f40
--- /dev/null
+++ b/lwext4/ext4_trans.c
@@ -0,0 +1,115 @@
+/*
+ * Copyright (c) 2015 Grzegorz Kostka (kostka.grzegorz@gmail.com)
+ * Copyright (c) 2015 Kaho Ng (ngkaho1234@gmail.com)
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ * derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup lwext4
+ * @{
+ */
+/**
+ * @file ext4.h
+ * @brief Ext4 transaction buffer operations.
+ */
+
+#include "ext4_config.h"
+#include "ext4_types.h"
+#include "ext4_journal.h"
+
+static int ext4_trans_get_write_access(struct ext4_fs *fs,
+ struct ext4_block *block)
+{
+ int r = EOK;
+ if (fs->jbd_journal && fs->curr_trans) {
+ struct jbd_journal *journal = fs->jbd_journal;
+ struct jbd_trans *trans = fs->curr_trans;
+ r = jbd_trans_get_access(journal, trans, block);
+ }
+ return r;
+}
+
+int ext4_trans_set_block_dirty(struct ext4_buf *buf)
+{
+ int r = EOK;
+ struct ext4_fs *fs = buf->bc->bdev->fs;
+ struct ext4_block block = {
+ .lb_id = buf->lba,
+ .data = buf->data,
+ .buf = buf
+ };
+
+ if (fs->jbd_journal && fs->curr_trans) {
+ struct jbd_trans *trans = fs->curr_trans;
+ r = jbd_trans_set_block_dirty(trans, &block);
+ } else
+ ext4_bcache_set_dirty(buf);
+
+ return r;
+}
+
+int ext4_trans_block_get_noread(struct ext4_blockdev *bdev,
+ struct ext4_block *b,
+ uint64_t lba)
+{
+ int r = ext4_block_get_noread(bdev, b, lba);
+ if (r != EOK)
+ return r;
+
+ if((r = ext4_trans_get_write_access(bdev->fs, b)) != EOK)
+ ext4_block_set(bdev, b);
+
+ return r;
+}
+
+int ext4_trans_block_get(struct ext4_blockdev *bdev,
+ struct ext4_block *b,
+ uint64_t lba)
+{
+ int r = ext4_block_get(bdev, b, lba);
+ if (r != EOK)
+ return r;
+
+ if((r = ext4_trans_get_write_access(bdev->fs, b)) != EOK)
+ ext4_block_set(bdev, b);
+
+ return r;
+}
+
+int ext4_trans_try_revoke_block(struct ext4_blockdev *bdev,
+ uint64_t lba)
+{
+ int r = EOK;
+ struct ext4_fs *fs = bdev->fs;
+ if (fs->jbd_journal && fs->curr_trans) {
+ struct jbd_trans *trans = fs->curr_trans;
+ jbd_trans_try_revoke_block(trans, lba);
+ }
+ return r;
+}
+
+/**
+ * @}
+ */
diff --git a/lwext4/ext4_trans.h b/lwext4/ext4_trans.h
new file mode 100644
index 0000000..e3cb28a
--- /dev/null
+++ b/lwext4/ext4_trans.h
@@ -0,0 +1,90 @@
+/*
+ * Copyright (c) 2015 Grzegorz Kostka (kostka.grzegorz@gmail.com)
+ * Copyright (c) 2015 Kaho Ng (ngkaho1234@gmail.com)
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * - Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * - Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * - The name of the author may not be used to endorse or promote products
+ * derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/** @addtogroup lwext4
+ * @{
+ */
+/**
+ * @file ext4_trans.h
+ * @brief Transaction handle functions
+ */
+
+#ifndef EXT4_TRANS_H
+#define EXT4_TRANS_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include "ext4_config.h"
+#include "ext4_types.h"
+
+
+/**@brief Mark a buffer dirty and add it to the current transaction.
+ * @param buf buffer
+ * @return standard error code*/
+int ext4_trans_set_block_dirty(struct ext4_buf *buf);
+
+/**@brief Block get function (through cache, don't read).
+ * jbd_trans_get_access would be called in order to
+ * get write access to the buffer.
+ * @param bdev block device descriptor
+ * @param b block descriptor
+ * @param lba logical block address
+ * @return standard error code*/
+int ext4_trans_block_get_noread(struct ext4_blockdev *bdev,
+ struct ext4_block *b,
+ uint64_t lba);
+
+/**@brief Block get function (through cache).
+ * jbd_trans_get_access would be called in order to
+ * get write access to the buffer.
+ * @param bdev block device descriptor
+ * @param b block descriptor
+ * @param lba logical block address
+ * @return standard error code*/
+int ext4_trans_block_get(struct ext4_blockdev *bdev,
+ struct ext4_block *b,
+ uint64_t lba);
+
+/**@brief Try to add block to be revoked to the current transaction.
+ * @param bdev block device descriptor
+ * @param lba logical block address
+ * @return standard error code*/
+int ext4_trans_try_revoke_block(struct ext4_blockdev *bdev,
+ uint64_t lba);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* EXT4_TRANS_H */
+
+/**
+ * @}
+ */
diff --git a/lwext4/ext4_xattr.c b/lwext4/ext4_xattr.c
index b446d62..b8465a7 100644
--- a/lwext4/ext4_xattr.c
+++ b/lwext4/ext4_xattr.c
@@ -543,7 +543,7 @@ static int ext4_xattr_try_alloc_block(struct ext4_xattr_ref *xattr_ref)
if (ret != EOK)
goto Finish;
- ret = ext4_block_get(xattr_ref->fs->bdev, &xattr_ref->block,
+ ret = ext4_trans_block_get(xattr_ref->fs->bdev, &xattr_ref->block,
xattr_block);
if (ret != EOK) {
ext4_balloc_free_block(xattr_ref->inode_ref,
@@ -655,7 +655,7 @@ static int ext4_xattr_write_to_disk(struct ext4_xattr_ref *xattr_ref)
block_data = (char *)block_header + block_size_rem;
block_size_rem -= sizeof(struct ext4_xattr_header);
- ext4_bcache_set_dirty(xattr_ref->block.buf);
+ ext4_trans_set_block_dirty(xattr_ref->block.buf);
} else {
/* We don't need an extra block.*/
if (xattr_ref->block_loaded) {
@@ -677,7 +677,7 @@ static int ext4_xattr_write_to_disk(struct ext4_xattr_ref *xattr_ref)
&xattr_ref->fs->sb, 0);
xattr_ref->inode_ref->dirty = true;
- ext4_bcache_set_dirty(xattr_ref->block.buf);
+ ext4_trans_set_block_dirty(xattr_ref->block.buf);
}
}
}
@@ -726,7 +726,7 @@ static int ext4_xattr_write_to_disk(struct ext4_xattr_ref *xattr_ref)
ext4_xattr_set_block_checksum(xattr_ref->inode_ref,
xattr_ref->block.lb_id,
block_header);
- ext4_bcache_set_dirty(xattr_ref->block.buf);
+ ext4_trans_set_block_dirty(xattr_ref->block.buf);
}
Finish:
@@ -837,7 +837,7 @@ int ext4_fs_get_xattr_ref(struct ext4_fs *fs, struct ext4_inode_ref *inode_ref,
ref->ea_size = 0;
ref->iter_from = NULL;
if (xattr_block) {
- rc = ext4_block_get(fs->bdev, &ref->block, xattr_block);
+ rc = ext4_trans_block_get(fs->bdev, &ref->block, xattr_block);
if (rc != EOK)
return EIO;