From 71674d00cf0105c99c64d4382c04a401f895f738 Mon Sep 17 00:00:00 2001 From: Vitaliy Filippov Date: Sun, 11 Jun 2023 11:09:22 +0300 Subject: [PATCH] Fix journal data checksum mangling on corrupted block overwrite --- src/blockstore_flush.cpp | 12 ++++++++---- src/blockstore_read.cpp | 4 ++-- 2 files changed, 10 insertions(+), 6 deletions(-) diff --git a/src/blockstore_flush.cpp b/src/blockstore_flush.cpp index 2a27da81..48e3e68b 100644 --- a/src/blockstore_flush.cpp +++ b/src/blockstore_flush.cpp @@ -773,13 +773,17 @@ bool journal_flusher_co::clear_incomplete_csum_block_bits(int wait_base) { bs->verify_journal_checksums(v[i].csum_buf, v[i].offset, &iov, 1, [&](uint32_t bad_block, uint32_t calc_csum, uint32_t stored_csum) { - printf("Checksum mismatch in object %lx:%lx v%lu in journal at offset 0x%lx+0x%x: got %08x, expected %08x\n", + printf("Checksum mismatch in object %lx:%lx v%lu in journal at offset 0x%lx+0x%x (block offset 0x%lx): got %08x, expected %08x\n", cur.oid.inode, cur.oid.stripe, old_clean_ver, - v[i].disk_offset, bad_block, calc_csum, stored_csum); - uint32_t bad_block_end = ((bad_block/bs->dsk.csum_block_size)+1)*bs->dsk.csum_block_size - - v[i].offset % bs->dsk.csum_block_size; + v[i].disk_offset, bad_block, v[i].offset, calc_csum, stored_csum); + bad_block += (v[i].offset/bs->dsk.csum_block_size) * bs->dsk.csum_block_size; + uint32_t bad_block_end = bad_block + bs->dsk.csum_block_size + (v[i].offset/bs->dsk.csum_block_size) * bs->dsk.csum_block_size; + if (bad_block < v[i].offset) + bad_block = v[i].offset; if (bad_block_end > v[i].offset+v[i].len) bad_block_end = v[i].offset+v[i].len; + bad_block -= v[i].offset; + bad_block_end -= v[i].offset; for (uint32_t j = bad_block; j < bad_block_end; j += bs->dsk.bitmap_granularity) { // Simplest method of mangling: flip one byte in every sector diff --git a/src/blockstore_read.cpp b/src/blockstore_read.cpp index 9b363672..d92de2e9 100644 --- a/src/blockstore_read.cpp +++ b/src/blockstore_read.cpp @@ -731,7 +731,7 @@ bool blockstore_impl_t::verify_journal_checksums(uint8_t *csums, uint32_t offset if (block_csum != ((uint32_t*)csums)[block_num]) { if (bad_block_cb) - bad_block_cb(block_num*dsk.csum_block_size - (offset%dsk.csum_block_size), block_csum, ((uint32_t*)csums)[block_num]); + bad_block_cb(block_num*dsk.csum_block_size, block_csum, ((uint32_t*)csums)[block_num]); else return false; } @@ -749,7 +749,7 @@ bool blockstore_impl_t::verify_journal_checksums(uint8_t *csums, uint32_t offset if (block_done > 0 && block_csum != ((uint32_t*)csums)[block_num]) { if (bad_block_cb) - bad_block_cb(block_num*dsk.csum_block_size - (offset%dsk.csum_block_size), block_csum, ((uint32_t*)csums)[block_num]); + bad_block_cb(block_num*dsk.csum_block_size, block_csum, ((uint32_t*)csums)[block_num]); else return false; }