ref: 0e2ae6f72708f8eb809762c18387edf289ac04a8
parent: 6be977907bea1aea635d208ad619ced763e7a125
author: Sigrid Solveig Haflínudóttir <sigrid@ftrv.se>
date: Wed Feb 14 19:39:22 EST 2024
ext4srv: faster crc32c
--- a/sys/src/cmd/ext4srv/ext4.c
+++ b/sys/src/cmd/ext4srv/ext4.c
@@ -8,6 +8,7 @@
#include "ext4_block_group.h"
#include "ext4_dir_idx.h"
#include "ext4_journal.h"
+#include "ext4_crc32.h"
char Eexists[] = "file exists";
char Einval[] = "invalid operation";
@@ -244,6 +245,7 @@
struct ext4_bcache *bc;
memset(mp, 0, sizeof(*mp));
+ ext4_crc32_init();
r = ext4_block_init(bd);
if (r != 0)
--- a/sys/src/cmd/ext4srv/ext4_balloc.c
+++ b/sys/src/cmd/ext4srv/ext4_balloc.c
@@ -41,16 +41,14 @@
return baddr;
}
-static u32int ext4_balloc_bitmap_csum(struct ext4_sblock *sb,
- void *bitmap)
+static u32int ext4_balloc_bitmap_csum(struct ext4_fs *fs, void *bitmap)
{
u32int checksum = 0;
- if (ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM)) {
- u32int blocks_per_group = ext4_get32(sb, blocks_per_group);
+ if (ext4_sb_feature_ro_com(&fs->sb, EXT4_FRO_COM_METADATA_CSUM)) {
+ u32int blocks_per_group = ext4_get32(&fs->sb, blocks_per_group);
/* First calculate crc32 checksum against fs uuid */
- checksum = ext4_crc32c(EXT4_CRC32_INIT, sb->uuid,
- sizeof(sb->uuid));
+ checksum = fs->uuid_crc32c;
/* Then calculate crc32 checksum against block_group_desc */
checksum = ext4_crc32c(checksum, bitmap, blocks_per_group / 8);
}
@@ -57,16 +55,16 @@
return checksum;
}
-void ext4_balloc_set_bitmap_csum(struct ext4_sblock *sb,
- struct ext4_bgroup *bg,
- void *bitmap)
+void ext4_balloc_set_bitmap_csum(struct ext4_fs *fs,
+ struct ext4_bgroup *bg,
+ void *bitmap)
{
- int desc_size = ext4_sb_get_desc_size(sb);
- u32int checksum = ext4_balloc_bitmap_csum(sb, bitmap);
+ int desc_size = ext4_sb_get_desc_size(&fs->sb);
+ u32int checksum = ext4_balloc_bitmap_csum(fs, bitmap);
u16int lo_checksum = to_le16(checksum & 0xFFFF),
hi_checksum = to_le16(checksum >> 16);
- if (!ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM))
+ if (!ext4_sb_feature_ro_com(&fs->sb, EXT4_FRO_COM_METADATA_CSUM))
return;
/* See if we need to assign a 32bit checksum */
@@ -77,12 +75,13 @@
}
static bool
-ext4_balloc_verify_bitmap_csum(struct ext4_sblock *sb,
- struct ext4_bgroup *bg,
- void *bitmap)
+ext4_balloc_verify_bitmap_csum(struct ext4_fs *fs,
+ struct ext4_bgroup *bg,
+ void *bitmap)
{
+ struct ext4_sblock *sb = &fs->sb;
int desc_size = ext4_sb_get_desc_size(sb);
- u32int checksum = ext4_balloc_bitmap_csum(sb, bitmap);
+ u32int checksum = ext4_balloc_bitmap_csum(fs, bitmap);
u16int lo_checksum = to_le16(checksum & 0xFFFF),
hi_checksum = to_le16(checksum >> 16);
@@ -127,7 +126,7 @@
return rc;
}
- if (!ext4_balloc_verify_bitmap_csum(sb, bg, bitmap_block.data)) {
+ if (!ext4_balloc_verify_bitmap_csum(fs, bg, bitmap_block.data)) {
ext4_dbg(DEBUG_BALLOC,
DBG_WARN "Bitmap checksum failed."
"Group: %ud\n",
@@ -136,7 +135,7 @@
/* Modify bitmap */
ext4_bmap_bit_clr(bitmap_block.data, index_in_group);
- ext4_balloc_set_bitmap_csum(sb, bg, bitmap_block.data);
+ ext4_balloc_set_bitmap_csum(fs, bg, bitmap_block.data);
ext4_trans_set_block_dirty(bitmap_block.buf);
/* Release block with bitmap */
@@ -228,7 +227,7 @@
return rc;
}
- if (!ext4_balloc_verify_bitmap_csum(sb, bg, blk.data)) {
+ if (!ext4_balloc_verify_bitmap_csum(fs, bg, blk.data)) {
ext4_dbg(DEBUG_BALLOC,
DBG_WARN "Bitmap checksum failed."
"Group: %ud\n",
@@ -242,7 +241,7 @@
/* Modify bitmap */
ext4_bmap_bits_free(blk.data, idx_in_bg_first, free_cnt);
- ext4_balloc_set_bitmap_csum(sb, bg, blk.data);
+ ext4_balloc_set_bitmap_csum(fs, bg, blk.data);
ext4_trans_set_block_dirty(blk.buf);
count -= free_cnt;
@@ -308,7 +307,8 @@
u32int rel_blk_idx = 0;
u64int free_blocks;
int r;
- struct ext4_sblock *sb = &inode_ref->fs->sb;
+ struct ext4_fs *fs = inode_ref->fs;
+ struct ext4_sblock *sb = &fs->sb;
/* Load block group number for goal and relative index */
u32int bg_id = ext4_balloc_get_bgid_of_block(sb, goal);
@@ -318,7 +318,7 @@
struct ext4_block_group_ref bg_ref;
/* Load block group reference */
- r = ext4_fs_get_block_group_ref(inode_ref->fs, bg_id, &bg_ref);
+ r = ext4_fs_get_block_group_ref(fs, bg_id, &bg_ref);
if (r != 0)
return r;
@@ -343,13 +343,13 @@
/* Load block with bitmap */
bmp_blk_adr = ext4_bg_get_block_bitmap(bg_ref.block_group, sb);
- r = ext4_trans_block_get(inode_ref->fs->bdev, &b, bmp_blk_adr);
+ r = ext4_trans_block_get(fs->bdev, &b, bmp_blk_adr);
if (r != 0) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
}
- if (!ext4_balloc_verify_bitmap_csum(sb, bg, b.data)) {
+ if (!ext4_balloc_verify_bitmap_csum(fs, bg, b.data)) {
ext4_dbg(DEBUG_BALLOC,
DBG_WARN "Bitmap checksum failed."
"Group: %ud\n",
@@ -359,10 +359,9 @@
/* Check if goal is free */
if (ext4_bmap_is_bit_clr(b.data, idx_in_bg)) {
ext4_bmap_bit_set(b.data, idx_in_bg);
- ext4_balloc_set_bitmap_csum(sb, bg_ref.block_group,
- b.data);
+ ext4_balloc_set_bitmap_csum(fs, bg_ref.block_group, b.data);
ext4_trans_set_block_dirty(b.buf);
- r = ext4_block_set(inode_ref->fs->bdev, &b);
+ r = ext4_block_set(fs->bdev, &b);
if (r != 0) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
@@ -384,9 +383,9 @@
if (ext4_bmap_is_bit_clr(b.data, tmp_idx)) {
ext4_bmap_bit_set(b.data, tmp_idx);
- ext4_balloc_set_bitmap_csum(sb, bg, b.data);
+ ext4_balloc_set_bitmap_csum(fs, bg, b.data);
ext4_trans_set_block_dirty(b.buf);
- r = ext4_block_set(inode_ref->fs->bdev, &b);
+ r = ext4_block_set(fs->bdev, &b);
if (r != 0) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
@@ -402,9 +401,9 @@
r = ext4_bmap_bit_find_clr(b.data, idx_in_bg, blk_in_bg, &rel_blk_idx, &no_space);
if (r == 0) {
ext4_bmap_bit_set(b.data, rel_blk_idx);
- ext4_balloc_set_bitmap_csum(sb, bg_ref.block_group, b.data);
+ ext4_balloc_set_bitmap_csum(fs, bg_ref.block_group, b.data);
ext4_trans_set_block_dirty(b.buf);
- r = ext4_block_set(inode_ref->fs->bdev, &b);
+ r = ext4_block_set(fs->bdev, &b);
if (r != 0) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
@@ -415,7 +414,7 @@
}
/* No free block found yet */
- r = ext4_block_set(inode_ref->fs->bdev, &b);
+ r = ext4_block_set(fs->bdev, &b);
if (r != 0) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
@@ -433,7 +432,7 @@
u32int count = block_group_count;
while (count > 0) {
- r = ext4_fs_get_block_group_ref(inode_ref->fs, bgid, &bg_ref);
+ r = ext4_fs_get_block_group_ref(fs, bgid, &bg_ref);
if (r != 0)
return r;
@@ -446,13 +445,13 @@
/* Load block with bitmap */
bmp_blk_adr = ext4_bg_get_block_bitmap(bg, sb);
- r = ext4_trans_block_get(inode_ref->fs->bdev, &b, bmp_blk_adr);
+ r = ext4_trans_block_get(fs->bdev, &b, bmp_blk_adr);
if (r != 0) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
}
- if (!ext4_balloc_verify_bitmap_csum(sb, bg, b.data)) {
+ if (!ext4_balloc_verify_bitmap_csum(fs, bg, b.data)) {
ext4_dbg(DEBUG_BALLOC,
DBG_WARN "Bitmap checksum failed."
"Group: %ud\n",
@@ -472,9 +471,9 @@
r = ext4_bmap_bit_find_clr(b.data, idx_in_bg, blk_in_bg, &rel_blk_idx, &no_space);
if (r == 0) {
ext4_bmap_bit_set(b.data, rel_blk_idx);
- ext4_balloc_set_bitmap_csum(sb, bg, b.data);
+ ext4_balloc_set_bitmap_csum(fs, bg, b.data);
ext4_trans_set_block_dirty(b.buf);
- r = ext4_block_set(inode_ref->fs->bdev, &b);
+ r = ext4_block_set(fs->bdev, &b);
if (r != 0) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
@@ -484,7 +483,7 @@
goto success;
}
- r = ext4_block_set(inode_ref->fs->bdev, &b);
+ r = ext4_block_set(fs->bdev, &b);
if (r != 0) {
ext4_fs_put_block_group_ref(&bg_ref);
return r;
@@ -563,7 +562,7 @@
return rc;
}
- if (!ext4_balloc_verify_bitmap_csum(sb, bg_ref.block_group, b.data)) {
+ if (!ext4_balloc_verify_bitmap_csum(fs, bg_ref.block_group, b.data)) {
ext4_dbg(DEBUG_BALLOC,
DBG_WARN "Bitmap checksum failed."
"Group: %ud\n",
@@ -576,7 +575,7 @@
/* Allocate block if possible */
if (*free) {
ext4_bmap_bit_set(b.data, index_in_group);
- ext4_balloc_set_bitmap_csum(sb, bg_ref.block_group, b.data);
+ ext4_balloc_set_bitmap_csum(fs, bg_ref.block_group, b.data);
ext4_trans_set_block_dirty(b.buf);
}
--- a/sys/src/cmd/ext4srv/ext4_crc32.c
+++ b/sys/src/cmd/ext4srv/ext4_crc32.c
@@ -68,77 +68,106 @@
/* (ross@guest.adelaide.edu.au.). This document is likely to be */
/* in the FTP archive "ftp.adelaide.edu.au/pub/rocksoft". */
/* */
-static const u32int crc32c_tab[256] = {
- 0x00000000L, 0xF26B8303L, 0xE13B70F7L, 0x1350F3F4L, 0xC79A971FL,
- 0x35F1141CL, 0x26A1E7E8L, 0xD4CA64EBL, 0x8AD958CFL, 0x78B2DBCCL,
- 0x6BE22838L, 0x9989AB3BL, 0x4D43CFD0L, 0xBF284CD3L, 0xAC78BF27L,
- 0x5E133C24L, 0x105EC76FL, 0xE235446CL, 0xF165B798L, 0x030E349BL,
- 0xD7C45070L, 0x25AFD373L, 0x36FF2087L, 0xC494A384L, 0x9A879FA0L,
- 0x68EC1CA3L, 0x7BBCEF57L, 0x89D76C54L, 0x5D1D08BFL, 0xAF768BBCL,
- 0xBC267848L, 0x4E4DFB4BL, 0x20BD8EDEL, 0xD2D60DDDL, 0xC186FE29L,
- 0x33ED7D2AL, 0xE72719C1L, 0x154C9AC2L, 0x061C6936L, 0xF477EA35L,
- 0xAA64D611L, 0x580F5512L, 0x4B5FA6E6L, 0xB93425E5L, 0x6DFE410EL,
- 0x9F95C20DL, 0x8CC531F9L, 0x7EAEB2FAL, 0x30E349B1L, 0xC288CAB2L,
- 0xD1D83946L, 0x23B3BA45L, 0xF779DEAEL, 0x05125DADL, 0x1642AE59L,
- 0xE4292D5AL, 0xBA3A117EL, 0x4851927DL, 0x5B016189L, 0xA96AE28AL,
- 0x7DA08661L, 0x8FCB0562L, 0x9C9BF696L, 0x6EF07595L, 0x417B1DBCL,
- 0xB3109EBFL, 0xA0406D4BL, 0x522BEE48L, 0x86E18AA3L, 0x748A09A0L,
- 0x67DAFA54L, 0x95B17957L, 0xCBA24573L, 0x39C9C670L, 0x2A993584L,
- 0xD8F2B687L, 0x0C38D26CL, 0xFE53516FL, 0xED03A29BL, 0x1F682198L,
- 0x5125DAD3L, 0xA34E59D0L, 0xB01EAA24L, 0x42752927L, 0x96BF4DCCL,
- 0x64D4CECFL, 0x77843D3BL, 0x85EFBE38L, 0xDBFC821CL, 0x2997011FL,
- 0x3AC7F2EBL, 0xC8AC71E8L, 0x1C661503L, 0xEE0D9600L, 0xFD5D65F4L,
- 0x0F36E6F7L, 0x61C69362L, 0x93AD1061L, 0x80FDE395L, 0x72966096L,
- 0xA65C047DL, 0x5437877EL, 0x4767748AL, 0xB50CF789L, 0xEB1FCBADL,
- 0x197448AEL, 0x0A24BB5AL, 0xF84F3859L, 0x2C855CB2L, 0xDEEEDFB1L,
- 0xCDBE2C45L, 0x3FD5AF46L, 0x7198540DL, 0x83F3D70EL, 0x90A324FAL,
- 0x62C8A7F9L, 0xB602C312L, 0x44694011L, 0x5739B3E5L, 0xA55230E6L,
- 0xFB410CC2L, 0x092A8FC1L, 0x1A7A7C35L, 0xE811FF36L, 0x3CDB9BDDL,
- 0xCEB018DEL, 0xDDE0EB2AL, 0x2F8B6829L, 0x82F63B78L, 0x709DB87BL,
- 0x63CD4B8FL, 0x91A6C88CL, 0x456CAC67L, 0xB7072F64L, 0xA457DC90L,
- 0x563C5F93L, 0x082F63B7L, 0xFA44E0B4L, 0xE9141340L, 0x1B7F9043L,
- 0xCFB5F4A8L, 0x3DDE77ABL, 0x2E8E845FL, 0xDCE5075CL, 0x92A8FC17L,
- 0x60C37F14L, 0x73938CE0L, 0x81F80FE3L, 0x55326B08L, 0xA759E80BL,
- 0xB4091BFFL, 0x466298FCL, 0x1871A4D8L, 0xEA1A27DBL, 0xF94AD42FL,
- 0x0B21572CL, 0xDFEB33C7L, 0x2D80B0C4L, 0x3ED04330L, 0xCCBBC033L,
- 0xA24BB5A6L, 0x502036A5L, 0x4370C551L, 0xB11B4652L, 0x65D122B9L,
- 0x97BAA1BAL, 0x84EA524EL, 0x7681D14DL, 0x2892ED69L, 0xDAF96E6AL,
- 0xC9A99D9EL, 0x3BC21E9DL, 0xEF087A76L, 0x1D63F975L, 0x0E330A81L,
- 0xFC588982L, 0xB21572C9L, 0x407EF1CAL, 0x532E023EL, 0xA145813DL,
- 0x758FE5D6L, 0x87E466D5L, 0x94B49521L, 0x66DF1622L, 0x38CC2A06L,
- 0xCAA7A905L, 0xD9F75AF1L, 0x2B9CD9F2L, 0xFF56BD19L, 0x0D3D3E1AL,
- 0x1E6DCDEEL, 0xEC064EEDL, 0xC38D26C4L, 0x31E6A5C7L, 0x22B65633L,
- 0xD0DDD530L, 0x0417B1DBL, 0xF67C32D8L, 0xE52CC12CL, 0x1747422FL,
- 0x49547E0BL, 0xBB3FFD08L, 0xA86F0EFCL, 0x5A048DFFL, 0x8ECEE914L,
- 0x7CA56A17L, 0x6FF599E3L, 0x9D9E1AE0L, 0xD3D3E1ABL, 0x21B862A8L,
- 0x32E8915CL, 0xC083125FL, 0x144976B4L, 0xE622F5B7L, 0xF5720643L,
- 0x07198540L, 0x590AB964L, 0xAB613A67L, 0xB831C993L, 0x4A5A4A90L,
- 0x9E902E7BL, 0x6CFBAD78L, 0x7FAB5E8CL, 0x8DC0DD8FL, 0xE330A81AL,
- 0x115B2B19L, 0x020BD8EDL, 0xF0605BEEL, 0x24AA3F05L, 0xD6C1BC06L,
- 0xC5914FF2L, 0x37FACCF1L, 0x69E9F0D5L, 0x9B8273D6L, 0x88D28022L,
- 0x7AB90321L, 0xAE7367CAL, 0x5C18E4C9L, 0x4F48173DL, 0xBD23943EL,
- 0xF36E6F75L, 0x0105EC76L, 0x12551F82L, 0xE03E9C81L, 0x34F4F86AL,
- 0xC69F7B69L, 0xD5CF889DL, 0x27A40B9EL, 0x79B737BAL, 0x8BDCB4B9L,
- 0x988C474DL, 0x6AE7C44EL, 0xBE2DA0A5L, 0x4C4623A6L, 0x5F16D052L,
- 0xAD7D5351L};
+u32int crc32c_tab[4][256] = {
+{
+ 0x00000000U, 0xf26b8303U, 0xe13b70f7U, 0x1350f3f4U, 0xc79a971fU,
+ 0x35f1141cU, 0x26a1e7e8U, 0xd4ca64ebU, 0x8ad958cfU, 0x78b2dbccU,
+ 0x6be22838U, 0x9989ab3bU, 0x4d43cfd0U, 0xbf284cd3U, 0xac78bf27U,
+ 0x5e133c24U, 0x105ec76fU, 0xe235446cU, 0xf165b798U, 0x030e349bU,
+ 0xd7c45070U, 0x25afd373U, 0x36ff2087U, 0xc494a384U, 0x9a879fa0U,
+ 0x68ec1ca3U, 0x7bbcef57U, 0x89d76c54U, 0x5d1d08bfU, 0xaf768bbcU,
+ 0xbc267848U, 0x4e4dfb4bU, 0x20bd8edeU, 0xd2d60dddU, 0xc186fe29U,
+ 0x33ed7d2aU, 0xe72719c1U, 0x154c9ac2U, 0x061c6936U, 0xf477ea35U,
+ 0xaa64d611U, 0x580f5512U, 0x4b5fa6e6U, 0xb93425e5U, 0x6dfe410eU,
+ 0x9f95c20dU, 0x8cc531f9U, 0x7eaeb2faU, 0x30e349b1U, 0xc288cab2U,
+ 0xd1d83946U, 0x23b3ba45U, 0xf779deaeU, 0x05125dadU, 0x1642ae59U,
+ 0xe4292d5aU, 0xba3a117eU, 0x4851927dU, 0x5b016189U, 0xa96ae28aU,
+ 0x7da08661U, 0x8fcb0562U, 0x9c9bf696U, 0x6ef07595U, 0x417b1dbcU,
+ 0xb3109ebfU, 0xa0406d4bU, 0x522bee48U, 0x86e18aa3U, 0x748a09a0U,
+ 0x67dafa54U, 0x95b17957U, 0xcba24573U, 0x39c9c670U, 0x2a993584U,
+ 0xd8f2b687U, 0x0c38d26cU, 0xfe53516fU, 0xed03a29bU, 0x1f682198U,
+ 0x5125dad3U, 0xa34e59d0U, 0xb01eaa24U, 0x42752927U, 0x96bf4dccU,
+ 0x64d4cecfU, 0x77843d3bU, 0x85efbe38U, 0xdbfc821cU, 0x2997011fU,
+ 0x3ac7f2ebU, 0xc8ac71e8U, 0x1c661503U, 0xee0d9600U, 0xfd5d65f4U,
+ 0x0f36e6f7U, 0x61c69362U, 0x93ad1061U, 0x80fde395U, 0x72966096U,
+ 0xa65c047dU, 0x5437877eU, 0x4767748aU, 0xb50cf789U, 0xeb1fcbadU,
+ 0x197448aeU, 0x0a24bb5aU, 0xf84f3859U, 0x2c855cb2U, 0xdeeedfb1U,
+ 0xcdbe2c45U, 0x3fd5af46U, 0x7198540dU, 0x83f3d70eU, 0x90a324faU,
+ 0x62c8a7f9U, 0xb602c312U, 0x44694011U, 0x5739b3e5U, 0xa55230e6U,
+ 0xfb410cc2U, 0x092a8fc1U, 0x1a7a7c35U, 0xe811ff36U, 0x3cdb9bddU,
+ 0xceb018deU, 0xdde0eb2aU, 0x2f8b6829U, 0x82f63b78U, 0x709db87bU,
+ 0x63cd4b8fU, 0x91a6c88cU, 0x456cac67U, 0xb7072f64U, 0xa457dc90U,
+ 0x563c5f93U, 0x082f63b7U, 0xfa44e0b4U, 0xe9141340U, 0x1b7f9043U,
+ 0xcfb5f4a8U, 0x3dde77abU, 0x2e8e845fU, 0xdce5075cU, 0x92a8fc17U,
+ 0x60c37f14U, 0x73938ce0U, 0x81f80fe3U, 0x55326b08U, 0xa759e80bU,
+ 0xb4091bffU, 0x466298fcU, 0x1871a4d8U, 0xea1a27dbU, 0xf94ad42fU,
+ 0x0b21572cU, 0xdfeb33c7U, 0x2d80b0c4U, 0x3ed04330U, 0xccbbc033U,
+ 0xa24bb5a6U, 0x502036a5U, 0x4370c551U, 0xb11b4652U, 0x65d122b9U,
+ 0x97baa1baU, 0x84ea524eU, 0x7681d14dU, 0x2892ed69U, 0xdaf96e6aU,
+ 0xc9a99d9eU, 0x3bc21e9dU, 0xef087a76U, 0x1d63f975U, 0x0e330a81U,
+ 0xfc588982U, 0xb21572c9U, 0x407ef1caU, 0x532e023eU, 0xa145813dU,
+ 0x758fe5d6U, 0x87e466d5U, 0x94b49521U, 0x66df1622U, 0x38cc2a06U,
+ 0xcaa7a905U, 0xd9f75af1U, 0x2b9cd9f2U, 0xff56bd19U, 0x0d3d3e1aU,
+ 0x1e6dcdeeU, 0xec064eedU, 0xc38d26c4U, 0x31e6a5c7U, 0x22b65633U,
+ 0xd0ddd530U, 0x0417b1dbU, 0xf67c32d8U, 0xe52cc12cU, 0x1747422fU,
+ 0x49547e0bU, 0xbb3ffd08U, 0xa86f0efcU, 0x5a048dffU, 0x8ecee914U,
+ 0x7ca56a17U, 0x6ff599e3U, 0x9d9e1ae0U, 0xd3d3e1abU, 0x21b862a8U,
+ 0x32e8915cU, 0xc083125fU, 0x144976b4U, 0xe622f5b7U, 0xf5720643U,
+ 0x07198540U, 0x590ab964U, 0xab613a67U, 0xb831c993U, 0x4a5a4a90U,
+ 0x9e902e7bU, 0x6cfbad78U, 0x7fab5e8cU, 0x8dc0dd8fU, 0xe330a81aU,
+ 0x115b2b19U, 0x020bd8edU, 0xf0605beeU, 0x24aa3f05U, 0xd6c1bc06U,
+ 0xc5914ff2U, 0x37faccf1U, 0x69e9f0d5U, 0x9b8273d6U, 0x88d28022U,
+ 0x7ab90321U, 0xae7367caU, 0x5c18e4c9U, 0x4f48173dU, 0xbd23943eU,
+ 0xf36e6f75U, 0x0105ec76U, 0x12551f82U, 0xe03e9c81U, 0x34f4f86aU,
+ 0xc69f7b69U, 0xd5cf889dU, 0x27a40b9eU, 0x79b737baU, 0x8bdcb4b9U,
+ 0x988c474dU, 0x6ae7c44eU, 0xbe2da0a5U, 0x4c4623a6U, 0x5f16d052U,
+ 0xad7d5351U
+}
+};
-static inline u32int crc32(u32int crc, const void *buf, u32int size,
- const u32int *tab)
+u32int ext4_crc32(u32int crc, const void *buf, u32int size)
{
const u8int *p = (const u8int *)buf;
-
while (size--)
- crc = tab[(crc ^ *p++) & 0xFF] ^ (crc >> 8);
-
- return (crc);
+ crc = crc32_tab[(crc ^ *p++) & 0xFF] ^ (crc >> 8);
+ return crc;
}
-u32int ext4_crc32(u32int crc, const void *buf, u32int size)
+u32int ext4_crc32c(u32int crc, const void *buf, u32int size)
{
- return crc32(crc, buf, size, crc32_tab);
+ const u8int *p = (const u8int *)buf;
+ while(size > 0 && ((uintptr)p & 3) != 0)
+ crc = crc32c_tab[0][(crc ^ *p++) & 0xFF] ^ (crc >> 8);
+
+ const u32int *p32 = (const u32int *)p;
+ while(size >= 4){
+ size -= 4;
+ crc ^= *p32++;
+ crc =
+ crc32c_tab[0][crc>>24] ^
+ crc32c_tab[1][(crc>>16) & 0xff] ^
+ crc32c_tab[2][(crc>>8) & 0xff] ^
+ crc32c_tab[3][crc & 0xff];
+ }
+
+ p = (const u8int *)p32;
+ while(size--)
+ crc = crc32c_tab[0][(crc ^ *p++) & 0xFF] ^ (crc >> 8);
+
+ return crc;
}
-u32int ext4_crc32c(u32int crc, const void *buf, u32int size)
+void
+ext4_crc32_init(void)
{
- return crc32(crc, buf, size, crc32c_tab);
+ static bool done = false;
+ int i, j;
+
+ if(done)
+ return;
+ for(i = 1; i < 4; i++){
+ for(j = 0; j < 256; j++)
+ crc32c_tab[i][j] = (crc32c_tab[i-1][j] >> 8) ^ crc32c_tab[0][crc32c_tab[i-1][j] & 0xff];
+ }
+ done = true;
}
--- a/sys/src/cmd/ext4srv/ext4_dir.c
+++ b/sys/src/cmd/ext4srv/ext4_dir.c
@@ -33,16 +33,15 @@
struct ext4_dir_en *dirent, int size)
{
u32int csum;
- struct ext4_sblock *sb = &inode_ref->fs->sb;
u32int ino_index = to_le32(inode_ref->index);
u32int ino_gen = to_le32(ext4_inode_get_generation(inode_ref->inode));
/* First calculate crc32 checksum against fs uuid */
- csum = ext4_crc32c(EXT4_CRC32_INIT, sb->uuid, sizeof(sb->uuid));
+ csum = inode_ref->fs->uuid_crc32c;
/* Then calculate crc32 checksum against inode number
* and inode generation */
- csum = ext4_crc32c(csum, &ino_index, sizeof(ino_index));
- csum = ext4_crc32c(csum, &ino_gen, sizeof(ino_gen));
+ csum = ext4_crc32_u(csum, ino_index);
+ csum = ext4_crc32_u(csum, ino_gen);
/* Finally calculate crc32 checksum against directory entries */
csum = ext4_crc32c(csum, dirent, size);
return csum;
--- a/sys/src/cmd/ext4srv/ext4_dir_idx.c
+++ b/sys/src/cmd/ext4srv/ext4_dir_idx.c
@@ -185,11 +185,11 @@
orig_cum = t->checksum;
t->checksum = 0;
/* First calculate crc32 checksum against fs uuid */
- csum = ext4_crc32c(EXT4_CRC32_INIT, sb->uuid, sizeof(sb->uuid));
+ csum = inode_ref->fs->uuid_crc32c;
/* Then calculate crc32 checksum against inode number
* and inode generation */
- csum = ext4_crc32c(csum, &ino_index, sizeof(ino_index));
- csum = ext4_crc32c(csum, &ino_gen, sizeof(ino_gen));
+ csum = ext4_crc32_u(csum, ino_index);
+ csum = ext4_crc32_u(csum, ino_gen);
/* After that calculate crc32 checksum against all the dx_entry */
csum = ext4_crc32c(csum, de, sz);
/* Finally calculate crc32 checksum for dx_tail */
--- a/sys/src/cmd/ext4srv/ext4_extent.c
+++ b/sys/src/cmd/ext4srv/ext4_extent.c
@@ -40,18 +40,14 @@
u32int ino_gen =
to_le32(ext4_inode_get_generation(inode_ref->inode));
/* First calculate crc32 checksum against fs uuid */
- checksum = ext4_crc32c(EXT4_CRC32_INIT, sb->uuid,
- sizeof(sb->uuid));
+ checksum = inode_ref->fs->uuid_crc32c;
/* Then calculate crc32 checksum against inode number
* and inode generation */
- checksum = ext4_crc32c(checksum, &ino_index,
- sizeof(ino_index));
- checksum = ext4_crc32c(checksum, &ino_gen,
- sizeof(ino_gen));
+ checksum = ext4_crc32_u(checksum, ino_index);
+ checksum = ext4_crc32_u(checksum, ino_gen);
/* Finally calculate crc32 checksum against
* the entire extent block up to the checksum field */
- checksum = ext4_crc32c(checksum, eh,
- EXT4_EXTENT_TAIL_OFFSET(eh));
+ checksum = ext4_crc32c(checksum, eh, EXT4_EXTENT_TAIL_OFFSET(eh));
}
return checksum;
}
--- a/sys/src/cmd/ext4srv/ext4_fs.c
+++ b/sys/src/cmd/ext4srv/ext4_fs.c
@@ -80,6 +80,9 @@
ext4_set16(&fs->sb, mount_count, ext4_get16(&fs->sb, mount_count) + 1);
}
+ if(r == 0)
+ fs->uuid_crc32c = ext4_crc32c(EXT4_CRC32_INIT, fs->sb.uuid, sizeof(fs->sb.uuid));
+
return r;
}
@@ -250,7 +253,8 @@
*/
static int ext4_fs_init_block_bitmap(struct ext4_block_group_ref *bg_ref)
{
- struct ext4_sblock *sb = &bg_ref->fs->sb;
+ struct ext4_fs *fs = bg_ref->fs;
+ struct ext4_sblock *sb = &fs->sb;
struct ext4_bgroup *bg = bg_ref->block_group;
int rc;
@@ -274,7 +278,7 @@
u32int inode_table_bcnt = inodes_per_group * inode_size / block_size;
struct ext4_block block_bitmap;
- rc = ext4_trans_block_get_noread(bg_ref->fs->bdev, &block_bitmap, bmp_blk);
+ rc = ext4_trans_block_get_noread(fs->bdev, &block_bitmap, bmp_blk);
if (rc != 0)
return rc;
@@ -333,11 +337,11 @@
ext4_fs_mark_bitmap_end(group_blocks, block_size * 8, block_bitmap.data);
ext4_trans_set_block_dirty(block_bitmap.buf);
- ext4_balloc_set_bitmap_csum(sb, bg_ref->block_group, block_bitmap.data);
+ ext4_balloc_set_bitmap_csum(fs, bg_ref->block_group, block_bitmap.data);
bg_ref->dirty = true;
/* Save bitmap */
- return ext4_block_set(bg_ref->fs->bdev, &block_bitmap);
+ return ext4_block_set(fs->bdev, &block_bitmap);
}
/**@brief Initialize i-node bitmap in block group.
@@ -376,7 +380,7 @@
ext4_trans_set_block_dirty(b.buf);
- ext4_ialloc_set_bitmap_csum(sb, bg, b.data);
+ ext4_ialloc_set_bitmap_csum(bg_ref->fs, bg, b.data);
bg_ref->dirty = true;
/* Save bitmap */
@@ -451,9 +455,10 @@
* @param bg Block group to compute checksum for
* @return Checksum value
*/
-static u16int ext4_fs_bg_checksum(struct ext4_sblock *sb, u32int bgid,
- struct ext4_bgroup *bg)
+static u16int ext4_fs_bg_checksum(struct ext4_fs *fs, u32int bgid, struct ext4_bgroup *bg)
{
+ struct ext4_sblock *sb = &fs->sb;
+
/* If checksum not supported, 0 will be returned */
u16int crc = 0;
@@ -468,10 +473,9 @@
bg->checksum = 0;
/* First calculate crc32 checksum against fs uuid */
- checksum = ext4_crc32c(EXT4_CRC32_INIT, sb->uuid,
- sizeof(sb->uuid));
+ checksum = fs->uuid_crc32c;
/* Then calculate crc32 checksum against bgid */
- checksum = ext4_crc32c(checksum, &le32_bgid, sizeof(bgid));
+ checksum = ext4_crc32_u(checksum, le32_bgid);
/* Finally calculate crc32 checksum against block_group_desc */
checksum = ext4_crc32c(checksum, bg, ext4_sb_get_desc_size(sb));
bg->checksum = orig_checksum;
@@ -514,14 +518,14 @@
return crc;
}
-static bool ext4_fs_verify_bg_csum(struct ext4_sblock *sb,
- u32int bgid,
- struct ext4_bgroup *bg)
+static bool ext4_fs_verify_bg_csum(struct ext4_fs *fs,
+ u32int bgid,
+ struct ext4_bgroup *bg)
{
- if (!ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM))
+ if (!ext4_sb_feature_ro_com(&fs->sb, EXT4_FRO_COM_METADATA_CSUM))
return true;
- return ext4_fs_bg_checksum(sb, bgid, bg) == to_le16(bg->checksum);
+ return ext4_fs_bg_checksum(fs, bgid, bg) == to_le16(bg->checksum);
}
int ext4_fs_get_block_group_ref(struct ext4_fs *fs, u32int bgid,
@@ -547,7 +551,7 @@
ref->dirty = false;
struct ext4_bgroup *bg = ref->block_group;
- if (!ext4_fs_verify_bg_csum(&fs->sb, bgid, bg)) {
+ if (!ext4_fs_verify_bg_csum(fs, bgid, bg)) {
ext4_dbg(DEBUG_FS,
DBG_WARN "Block group descriptor checksum failed."
"Block group index: %ud\n",
@@ -595,8 +599,7 @@
if (ref->dirty) {
/* Compute new checksum of block group */
u16int cs;
- cs = ext4_fs_bg_checksum(&ref->fs->sb, ref->index,
- ref->block_group);
+ cs = ext4_fs_bg_checksum(ref->fs, ref->index, ref->block_group);
ref->block_group->checksum = to_le16(cs);
/* Mark block dirty for writing changes to physical device */
@@ -625,12 +628,11 @@
ext4_inode_set_csum(sb, inode_ref->inode, 0);
/* First calculate crc32 checksum against fs uuid */
- checksum = ext4_crc32c(EXT4_CRC32_INIT, sb->uuid,
- sizeof(sb->uuid));
+ checksum = inode_ref->fs->uuid_crc32c;
/* Then calculate crc32 checksum against inode number
* and inode generation */
- checksum = ext4_crc32c(checksum, &ino_index, sizeof(ino_index));
- checksum = ext4_crc32c(checksum, &ino_gen, sizeof(ino_gen));
+ checksum = ext4_crc32_u(checksum, ino_index);
+ checksum = ext4_crc32_u(checksum, ino_gen);
/* Finally calculate crc32 checksum against
* the entire inode */
checksum = ext4_crc32c(checksum, inode_ref->inode, inode_size);
--- a/sys/src/cmd/ext4srv/ext4_ialloc.c
+++ b/sys/src/cmd/ext4srv/ext4_ialloc.c
@@ -48,15 +48,15 @@
return (inode - 1) / inodes_per_group;
}
-static u32int ext4_ialloc_bitmap_csum(struct ext4_sblock *sb, void *bitmap)
+static u32int ext4_ialloc_bitmap_csum(struct ext4_fs *fs, void *bitmap)
{
u32int csum = 0;
- if (ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM)) {
+ if (ext4_sb_feature_ro_com(&fs->sb, EXT4_FRO_COM_METADATA_CSUM)) {
u32int inodes_per_group =
- ext4_get32(sb, inodes_per_group);
+ ext4_get32(&fs->sb, inodes_per_group);
/* First calculate crc32 checksum against fs uuid */
- csum = ext4_crc32c(EXT4_CRC32_INIT, sb->uuid, sizeof(sb->uuid));
+ csum = fs->uuid_crc32c;
/* Then calculate crc32 checksum against inode bitmap */
csum = ext4_crc32c(csum, bitmap, (inodes_per_group + 7) / 8);
}
@@ -63,14 +63,14 @@
return csum;
}
-void ext4_ialloc_set_bitmap_csum(struct ext4_sblock *sb, struct ext4_bgroup *bg, void *bitmap)
+void ext4_ialloc_set_bitmap_csum(struct ext4_fs *fs, struct ext4_bgroup *bg, void *bitmap)
{
- int desc_size = ext4_sb_get_desc_size(sb);
- u32int csum = ext4_ialloc_bitmap_csum(sb, bitmap);
+ int desc_size = ext4_sb_get_desc_size(&fs->sb);
+ u32int csum = ext4_ialloc_bitmap_csum(fs, bitmap);
u16int lo_csum = to_le16(csum & 0xFFFF),
hi_csum = to_le16(csum >> 16);
- if (!ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM))
+ if (!ext4_sb_feature_ro_com(&fs->sb, EXT4_FRO_COM_METADATA_CSUM))
return;
/* See if we need to assign a 32bit checksum */
@@ -81,14 +81,14 @@
}
static bool
-ext4_ialloc_verify_bitmap_csum(struct ext4_sblock *sb, struct ext4_bgroup *bg, void *bitmap)
+ext4_ialloc_verify_bitmap_csum(struct ext4_fs *fs, struct ext4_bgroup *bg, void *bitmap)
{
- int desc_size = ext4_sb_get_desc_size(sb);
- u32int csum = ext4_ialloc_bitmap_csum(sb, bitmap);
+ int desc_size = ext4_sb_get_desc_size(&fs->sb);
+ u32int csum = ext4_ialloc_bitmap_csum(fs, bitmap);
u16int lo_csum = to_le16(csum & 0xFFFF),
hi_csum = to_le16(csum >> 16);
- if (!ext4_sb_feature_ro_com(sb, EXT4_FRO_COM_METADATA_CSUM))
+ if (!ext4_sb_feature_ro_com(&fs->sb, EXT4_FRO_COM_METADATA_CSUM))
return true;
if (bg->inode_bitmap_csum_lo != lo_csum)
@@ -124,7 +124,7 @@
if (rc != 0)
return rc;
- if (!ext4_ialloc_verify_bitmap_csum(sb, bg, b.data)) {
+ if (!ext4_ialloc_verify_bitmap_csum(fs, bg, b.data)) {
ext4_dbg(DEBUG_IALLOC,
DBG_WARN "Bitmap checksum failed."
"Group: %ud\n",
@@ -134,7 +134,7 @@
/* Free i-node in the bitmap */
u32int 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_ialloc_set_bitmap_csum(fs, bg, b.data);
ext4_trans_set_block_dirty(b.buf);
/* Put back the block with bitmap */
@@ -217,7 +217,7 @@
return rc;
}
- if (!ext4_ialloc_verify_bitmap_csum(sb, bg, b.data)) {
+ if (!ext4_ialloc_verify_bitmap_csum(fs, bg, b.data)) {
ext4_dbg(DEBUG_IALLOC,
DBG_WARN "Bitmap checksum failed."
"Group: %ud\n",
@@ -249,8 +249,7 @@
ext4_bmap_bit_set(b.data, idx_in_bg);
/* Free i-node found, save the bitmap */
- ext4_ialloc_set_bitmap_csum(sb,bg,
- b.data);
+ ext4_ialloc_set_bitmap_csum(fs, bg, b.data);
ext4_trans_set_block_dirty(b.buf);
ext4_block_set(fs->bdev, &b);
--- a/sys/src/cmd/ext4srv/ext4_journal.c
+++ b/sys/src/cmd/ext4srv/ext4_journal.c
@@ -126,9 +126,8 @@
if (jbd_has_csum(jbd_sb)) {
u32int orig_checksum = jbd_sb->checksum;
jbd_set32(jbd_sb, checksum, 0);
- /* Calculate crc32c checksum against tho whole superblock */
- checksum = ext4_crc32c(EXT4_CRC32_INIT, jbd_sb,
- JBD_SUPERBLOCK_SIZE);
+ /* Calculate crc32c checksum against the whole superblock */
+ checksum = ext4_crc32c(EXT4_CRC32_INIT, jbd_sb, JBD_SUPERBLOCK_SIZE);
jbd_sb->checksum = orig_checksum;
}
return checksum;
@@ -165,11 +164,9 @@
tail->checksum = 0;
/* First calculate crc32c checksum against fs uuid */
- checksum = ext4_crc32c(EXT4_CRC32_INIT, jbd_fs->sb.uuid,
- sizeof(jbd_fs->sb.uuid));
+ checksum = jbd_fs->uuid_crc32c;
/* Calculate crc32c checksum against tho whole block */
- checksum = ext4_crc32c(checksum, bhdr,
- block_size);
+ checksum = ext4_crc32c(checksum, bhdr, block_size);
tail->checksum = orig_checksum;
}
return checksum;
@@ -217,11 +214,9 @@
header->chksum[0] = 0;
/* First calculate crc32c checksum against fs uuid */
- checksum = ext4_crc32c(EXT4_CRC32_INIT, jbd_fs->sb.uuid,
- sizeof(jbd_fs->sb.uuid));
+ checksum = jbd_fs->uuid_crc32c;
/* Calculate crc32c checksum against tho whole block */
- checksum = ext4_crc32c(checksum, header,
- block_size);
+ checksum = ext4_crc32c(checksum, header, block_size);
header->chksum_type = orig_checksum_type;
header->chksum_size = orig_checksum_size;
@@ -264,20 +259,16 @@
if (jbd_has_csum(&jbd_fs->sb)) {
u32int block_size = jbd_get32(&jbd_fs->sb, blocksize);
/* First calculate crc32c checksum against fs uuid */
- checksum = ext4_crc32c(EXT4_CRC32_INIT, jbd_fs->sb.uuid,
- sizeof(jbd_fs->sb.uuid));
+ checksum = jbd_fs->uuid_crc32c;
/* Then calculate crc32c checksum against sequence no. */
- checksum = ext4_crc32c(checksum, &sequence,
- sizeof(u32int));
- /* Calculate crc32c checksum against tho whole block */
- checksum = ext4_crc32c(checksum, buf,
- block_size);
+ checksum = ext4_crc32_u(checksum, sequence);
+ /* Calculate crc32c checksum against the whole block */
+ checksum = ext4_crc32c(checksum, buf, block_size);
} else if (JBD_HAS_INCOMPAT_FEATURE(&jbd_fs->sb,
JBD_FEATURE_COMPAT_CHECKSUM)) {
u32int block_size = jbd_get32(&jbd_fs->sb, blocksize);
- /* Calculate crc32c checksum against tho whole block */
- checksum = ext4_crc32(csum, buf,
- block_size);
+ /* Calculate crc32 checksum against the whole block */
+ checksum = ext4_crc32(csum, buf, block_size);
}
return checksum;
}
--- a/sys/src/cmd/ext4srv/ext4_super.c
+++ b/sys/src/cmd/ext4srv/ext4_super.c
@@ -44,9 +44,7 @@
static u32int ext4_sb_csum(struct ext4_sblock *s)
{
-
- return ext4_crc32c(EXT4_CRC32_INIT, s,
- offsetof(struct ext4_sblock, checksum));
+ return ext4_crc32c(EXT4_CRC32_INIT, s, offsetof(struct ext4_sblock, checksum));
}
static bool ext4_sb_verify_csum(struct ext4_sblock *s)
--- a/sys/src/cmd/ext4srv/include/ext4_balloc.h
+++ b/sys/src/cmd/ext4srv/include/ext4_balloc.h
@@ -25,9 +25,9 @@
* @param bg block group
* @param bitmap bitmap buffer
*/
-void ext4_balloc_set_bitmap_csum(struct ext4_sblock *sb,
- struct ext4_bgroup *bg,
- void *bitmap);
+void ext4_balloc_set_bitmap_csum(struct ext4_fs *fs,
+ struct ext4_bgroup *bg,
+ void *bitmap);
/**@brief Free block from inode.
* @param inode_ref inode reference
--- a/sys/src/cmd/ext4srv/include/ext4_crc32.h
+++ b/sys/src/cmd/ext4srv/include/ext4_crc32.h
@@ -10,6 +10,8 @@
* @return updated crc32 value*/
u32int ext4_crc32(u32int crc, const void *buf, u32int size);
+extern u32int crc32c_tab[4][256];
+
/**@brief CRC32C algorithm.
* @param crc input feed
* @param buf input buffer
@@ -16,3 +18,13 @@
* @param length input buffer length (bytes)
* @return updated crc32c value*/
u32int ext4_crc32c(u32int crc, const void *buf, u32int size);
+
+#define ext4_crc32_u(crc, x) ( \
+ (crc) = (crc) ^ (x), \
+ crc32c_tab[0][(crc)>>24] ^ \
+ crc32c_tab[1][((crc)>>16) & 0xff] ^ \
+ crc32c_tab[2][((crc)>>8) & 0xff] ^ \
+ crc32c_tab[3][(crc) & 0xff] \
+)
+
+void ext4_crc32_init(void);
--- a/sys/src/cmd/ext4srv/include/ext4_fs.h
+++ b/sys/src/cmd/ext4srv/include/ext4_fs.h
@@ -9,6 +9,7 @@
struct ext4_blockdev *bdev;
struct ext4_sblock sb;
+ u32int uuid_crc32c;
u64int inode_block_limits[4];
u64int inode_blocks_per_level[4];
--- a/sys/src/cmd/ext4srv/include/ext4_ialloc.h
+++ b/sys/src/cmd/ext4srv/include/ext4_ialloc.h
@@ -4,11 +4,11 @@
#include "ext4_types.h"
/**@brief Calculate and set checksum of inode bitmap.
- * @param sb superblock pointer.
+ * @param fs fs pointer.
* @param bg block group
* @param bitmap bitmap buffer
*/
-void ext4_ialloc_set_bitmap_csum(struct ext4_sblock *sb, struct ext4_bgroup *bg,
+void ext4_ialloc_set_bitmap_csum(struct ext4_fs *fs, struct ext4_bgroup *bg,
void *bitmap);
/**@brief Free i-node number and modify filesystem data structers.
--- a/sys/src/cmd/ext4srv/include/ext4_journal.h
+++ b/sys/src/cmd/ext4srv/include/ext4_journal.h
@@ -9,6 +9,7 @@
struct ext4_blockdev *bdev;
struct ext4_inode_ref inode_ref;
struct jbd_sb sb;
+ u32int uuid_crc32c;
bool dirty;
};