Fix type mismatch.
[lwext4.git] / src / ext4_fs.c
index 392728dd8040765e6026f8564d03e1416ac9ce47..77073410d44962dfdc22fc1e01d8e4382678c4d6 100644 (file)
 
 #include "ext4_config.h"
 #include "ext4_types.h"
-#include "ext4_fs.h"
+#include "ext4_misc.h"
 #include "ext4_errno.h"
+#include "ext4_debug.h"
+
+#include "ext4_trans.h"
+#include "ext4_fs.h"
 #include "ext4_blockdev.h"
 #include "ext4_super.h"
 #include "ext4_crc32.h"
-#include "ext4_debug.h"
 #include "ext4_block_group.h"
 #include "ext4_balloc.h"
 #include "ext4_bitmap.h"
 
 #include <string.h>
 
-int ext4_fs_init(struct ext4_fs *fs, struct ext4_blockdev *bdev)
+int ext4_fs_init(struct ext4_fs *fs, struct ext4_blockdev *bdev,
+                bool read_only)
 {
        int r, i;
        uint16_t tmp;
        uint32_t bsize;
-       bool read_only = false;
 
        ext4_assert(fs && bdev);
 
        fs->bdev = bdev;
 
+       fs->read_only = read_only;
+
        r = ext4_sb_read(fs->bdev, &fs->sb);
        if (r != EOK)
                return r;
@@ -82,7 +87,7 @@ int ext4_fs_init(struct ext4_fs *fs, struct ext4_blockdev *bdev)
                return r;
 
        if (read_only)
-               return ENOTSUP;
+               fs->read_only = read_only;
 
        /* Compute limits for indirect block levels */
        uint32_t blocks_id = bsize / sizeof(uint32_t);
@@ -104,14 +109,16 @@ int ext4_fs_init(struct ext4_fs *fs, struct ext4_blockdev *bdev)
                                "last umount error: superblock fs_error flag\n");
 
 
-       /* Mark system as mounted */
-       ext4_set16(&fs->sb, state, EXT4_SUPERBLOCK_STATE_ERROR_FS);
-       r = ext4_sb_write(fs->bdev, &fs->sb);
-       if (r != EOK)
-               return r;
+       if (!fs->read_only) {
+               /* Mark system as mounted */
+               ext4_set16(&fs->sb, state, EXT4_SUPERBLOCK_STATE_ERROR_FS);
+               r = ext4_sb_write(fs->bdev, &fs->sb);
+               if (r != EOK)
+                       return r;
 
-       /*Update mount count*/
-       ext4_set16(&fs->sb, mount_count, ext4_get16(&fs->sb, mount_count) + 1);
+               /*Update mount count*/
+               ext4_set16(&fs->sb, mount_count, ext4_get16(&fs->sb, mount_count) + 1);
+       }
 
        return r;
 }
@@ -123,7 +130,10 @@ int ext4_fs_fini(struct ext4_fs *fs)
        /*Set superblock state*/
        ext4_set16(&fs->sb, state, EXT4_SUPERBLOCK_STATE_VALID_FS);
 
-       return ext4_sb_write(fs->bdev, &fs->sb);
+       if (!fs->read_only)
+               return ext4_sb_write(fs->bdev, &fs->sb);
+
+       return EOK;
 }
 
 static void ext4_fs_debug_features_inc(uint32_t features_incompatible)
@@ -283,12 +293,13 @@ static int ext4_fs_init_block_bitmap(struct ext4_block_group_ref *bg_ref)
        struct ext4_bgroup *bg = bg_ref->block_group;
        int rc;
 
-       uint32_t i, bit, bit_max;
+       uint32_t bit, bit_max;
        uint32_t group_blocks;
        uint16_t inode_size = ext4_get16(sb, inode_size);
        uint32_t block_size = ext4_sb_get_block_size(sb);
        uint32_t inodes_per_group = ext4_get32(sb, inodes_per_group);
 
+       ext4_fsblk_t i;
        ext4_fsblk_t bmp_blk = ext4_bg_get_block_bitmap(bg, sb);
        ext4_fsblk_t bmp_inode = ext4_bg_get_inode_bitmap(bg, sb);
        ext4_fsblk_t inode_table = ext4_bg_get_inode_table_first_block(bg, sb);
@@ -1052,7 +1063,7 @@ finish:
  * @return Error code
  */
 static int ext4_fs_release_inode_block(struct ext4_inode_ref *inode_ref,
-                               uint32_t iblock)
+                               ext4_lblk_t iblock)
 {
        ext4_fsblk_t fblock;
 
@@ -1093,11 +1104,11 @@ static int ext4_fs_release_inode_block(struct ext4_inode_ref *inode_ref,
 
        /* Compute offsets for the topmost level */
        uint32_t block_offset_in_level =
-           iblock - fs->inode_block_limits[level - 1];
+               (uint32_t)(iblock - fs->inode_block_limits[level - 1]);
        ext4_fsblk_t current_block =
            ext4_inode_get_indirect_block(inode, level - 1);
        uint32_t offset_in_block =
-           block_offset_in_level / fs->inode_blocks_per_level[level - 1];
+           (uint32_t)(block_offset_in_level / fs->inode_blocks_per_level[level - 1]);
 
        /*
         * Navigate through other levels, until we find the block number
@@ -1139,8 +1150,8 @@ static int ext4_fs_release_inode_block(struct ext4_inode_ref *inode_ref,
 
                /* Visit the next level */
                block_offset_in_level %= fs->inode_blocks_per_level[level];
-               offset_in_block = block_offset_in_level /
-                                 fs->inode_blocks_per_level[level - 1];
+               offset_in_block = (uint32_t)(block_offset_in_level /
+                                 fs->inode_blocks_per_level[level - 1]);
        }
 
        fblock = current_block;
@@ -1308,7 +1319,7 @@ int ext4_fs_indirect_find_goal(struct ext4_inode_ref *inode_ref,
 }
 
 static int ext4_fs_get_inode_dblk_idx_internal(struct ext4_inode_ref *inode_ref,
-                                      uint64_t iblock, ext4_fsblk_t *fblock,
+                                      ext4_lblk_t iblock, ext4_fsblk_t *fblock,
                                       bool extent_create,
                                       bool support_unwritten __unused)
 {
@@ -1366,9 +1377,9 @@ static int ext4_fs_get_inode_dblk_idx_internal(struct ext4_inode_ref *inode_ref,
                return EIO;
 
        /* Compute offsets for the topmost level */
-       uint32_t blk_off_in_lvl =  iblock - fs->inode_block_limits[l - 1];
+       uint32_t blk_off_in_lvl = (uint32_t)(iblock - fs->inode_block_limits[l - 1]);
        current_block = ext4_inode_get_indirect_block(inode, l - 1);
-       uint32_t off_in_blk = blk_off_in_lvl / fs->inode_blocks_per_level[l - 1];
+       uint32_t off_in_blk = (uint32_t)(blk_off_in_lvl / fs->inode_blocks_per_level[l - 1]);
 
        /* Sparse file */
        if (current_block == 0) {
@@ -1413,7 +1424,7 @@ static int ext4_fs_get_inode_dblk_idx_internal(struct ext4_inode_ref *inode_ref,
 
                /* Visit the next level */
                blk_off_in_lvl %= fs->inode_blocks_per_level[l];
-               off_in_blk = blk_off_in_lvl / fs->inode_blocks_per_level[l - 1];
+               off_in_blk = (uint32_t)(blk_off_in_lvl / fs->inode_blocks_per_level[l - 1]);
        }
 
        *fblock = current_block;
@@ -1423,7 +1434,7 @@ static int ext4_fs_get_inode_dblk_idx_internal(struct ext4_inode_ref *inode_ref,
 
 
 int ext4_fs_get_inode_dblk_idx(struct ext4_inode_ref *inode_ref,
-                              uint64_t iblock, ext4_fsblk_t *fblock,
+                              ext4_lblk_t iblock, ext4_fsblk_t *fblock,
                               bool support_unwritten)
 {
        return ext4_fs_get_inode_dblk_idx_internal(inode_ref, iblock, fblock,
@@ -1431,14 +1442,14 @@ int ext4_fs_get_inode_dblk_idx(struct ext4_inode_ref *inode_ref,
 }
 
 int ext4_fs_init_inode_dblk_idx(struct ext4_inode_ref *inode_ref,
-                               uint64_t iblock, ext4_fsblk_t *fblock)
+                               ext4_lblk_t iblock, ext4_fsblk_t *fblock)
 {
        return ext4_fs_get_inode_dblk_idx_internal(inode_ref, iblock, fblock,
                                                   true, true);
 }
 
 static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
-                                      uint32_t iblock, ext4_fsblk_t fblock)
+                                      ext4_lblk_t iblock, ext4_fsblk_t fblock)
 {
        struct ext4_fs *fs = inode_ref->fs;
 
@@ -1476,10 +1487,10 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
        uint32_t block_size = ext4_sb_get_block_size(&fs->sb);
 
        /* Compute offsets for the topmost level */
-       uint32_t blk_off_in_lvl =  iblock - fs->inode_block_limits[l - 1];
+       uint32_t blk_off_in_lvl = (uint32_t)(iblock - fs->inode_block_limits[l - 1]);
        ext4_fsblk_t current_block =
                        ext4_inode_get_indirect_block(inode_ref->inode, l - 1);
-       uint32_t off_in_blk = blk_off_in_lvl / fs->inode_blocks_per_level[l - 1];
+       uint32_t off_in_blk = (uint32_t)(blk_off_in_lvl / fs->inode_blocks_per_level[l - 1]);
 
        ext4_fsblk_t new_blk;
 
@@ -1596,7 +1607,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
 
                /* Visit the next level */
                blk_off_in_lvl %= fs->inode_blocks_per_level[l];
-               off_in_blk = blk_off_in_lvl / fs->inode_blocks_per_level[l - 1];
+               off_in_blk = (uint32_t)(blk_off_in_lvl / fs->inode_blocks_per_level[l - 1]);
        }
 
        return EOK;
@@ -1604,7 +1615,7 @@ static int ext4_fs_set_inode_data_block_index(struct ext4_inode_ref *inode_ref,
 
 
 int ext4_fs_append_inode_dblk(struct ext4_inode_ref *inode_ref,
-                             ext4_fsblk_t *fblock, uint32_t *iblock)
+                             ext4_fsblk_t *fblock, ext4_lblk_t *iblock)
 {
 #if CONFIG_EXTENT_ENABLE
        /* Handle extents separately */