+#if CONFIG_META_CSUM_ENABLE
+static uint32_t ext4_ialloc_bitmap_csum(struct ext4_sblock *sb, void *bitmap)
+{
+ uint32_t csum = 0;
+ if (ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM)) {
+ uint32_t inodes_per_group =
+ ext4_get32(sb, inodes_per_group);
+
+ /* First calculate crc32 checksum against fs uuid */
+ csum = ext4_crc32c(EXT4_CRC32_INIT, sb->uuid, sizeof(sb->uuid));
+ /* Then calculate crc32 checksum against inode bitmap */
+ csum = ext4_crc32c(csum, bitmap, (inodes_per_group + 7) / 8);
+ }
+ return csum;
+}
+#else
+#define ext4_ialloc_bitmap_csum(...) 0
+#endif
+
+void ext4_ialloc_set_bitmap_csum(struct ext4_sblock *sb, struct ext4_bgroup *bg,
+ void *bitmap __unused)
+{
+ int desc_size = ext4_sb_get_desc_size(sb);
+ uint32_t csum = ext4_ialloc_bitmap_csum(sb, bitmap);
+ uint16_t lo_csum = to_le16(csum & 0xFFFF),
+ hi_csum = to_le16(csum >> 16);
+
+ if (!ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM))
+ return;
+
+ /* See if we need to assign a 32bit checksum */
+ bg->inode_bitmap_csum_lo = lo_csum;
+ if (desc_size == EXT4_MAX_BLOCK_GROUP_DESCRIPTOR_SIZE)
+ bg->inode_bitmap_csum_hi = hi_csum;
+
+}
+
+#if CONFIG_META_CSUM_ENABLE
+static bool
+ext4_ialloc_verify_bitmap_csum(struct ext4_sblock *sb, struct ext4_bgroup *bg,
+ void *bitmap __unused)
+{
+
+ int desc_size = ext4_sb_get_desc_size(sb);
+ uint32_t csum = ext4_ialloc_bitmap_csum(sb, bitmap);
+ uint16_t lo_csum = to_le16(csum & 0xFFFF),
+ hi_csum = to_le16(csum >> 16);
+
+ if (!ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM))
+ return true;
+
+ if (bg->inode_bitmap_csum_lo != lo_csum)
+ return false;
+
+ if (desc_size == EXT4_MAX_BLOCK_GROUP_DESCRIPTOR_SIZE)
+ if (bg->inode_bitmap_csum_hi != hi_csum)
+ return false;
+
+ return true;
+}
+#else
+#define ext4_ialloc_verify_bitmap_csum(...) true
+#endif
+