feat(compress): move block-state confirmation to Rust
Keep C ownership of the block-state structure while delegating the confirmed-block pointer swap through a narrow two-pointer ABI leaf. Preserve every existing confirmation call site and add direct pointer-swap coverage. Test Plan: - cargo test --manifest-path rust/Cargo.toml --no-default-features --features compression - cargo clippy --manifest-path rust/Cargo.toml --no-default-features --features compression --all-targets - cargo +nightly fmt --manifest-path rust/Cargo.toml - make -B -C lib -j2 lib - tests/fuzzer -s4560 -t47 -i48 -v - make -C tests -j2 test-zstream
This commit is contained in:
@@ -269,6 +269,9 @@ size_t ZSTD_rust_copyBlockSequences(
|
|||||||
SeqCollector* seqCollector, const SeqStore_t* seqStore,
|
SeqCollector* seqCollector, const SeqStore_t* seqStore,
|
||||||
const U32 prevRepcodes[ZSTD_REP_NUM]);
|
const U32 prevRepcodes[ZSTD_REP_NUM]);
|
||||||
void ZSTD_rust_resetCompressedBlockState(ZSTD_compressedBlockState_t* bs);
|
void ZSTD_rust_resetCompressedBlockState(ZSTD_compressedBlockState_t* bs);
|
||||||
|
void ZSTD_rust_confirmRepcodesAndEntropyTables(
|
||||||
|
ZSTD_compressedBlockState_t** prevCBlock,
|
||||||
|
ZSTD_compressedBlockState_t** nextCBlock);
|
||||||
void ZSTD_rust_storeLastLiterals(SeqStore_t* seqStorePtr,
|
void ZSTD_rust_storeLastLiterals(SeqStore_t* seqStorePtr,
|
||||||
const BYTE* anchor, size_t lastLLSize);
|
const BYTE* anchor, size_t lastLLSize);
|
||||||
void ZSTD_rust_resetSeqStore(SeqStore_t* ssPtr);
|
void ZSTD_rust_resetSeqStore(SeqStore_t* ssPtr);
|
||||||
@@ -2596,9 +2599,8 @@ static int ZSTD_maybeRLE(SeqStore_t const* seqStore)
|
|||||||
static void
|
static void
|
||||||
ZSTD_blockState_confirmRepcodesAndEntropyTables(ZSTD_blockState_t* const bs)
|
ZSTD_blockState_confirmRepcodesAndEntropyTables(ZSTD_blockState_t* const bs)
|
||||||
{
|
{
|
||||||
ZSTD_compressedBlockState_t* const tmp = bs->prevCBlock;
|
ZSTD_rust_confirmRepcodesAndEntropyTables(
|
||||||
bs->prevCBlock = bs->nextCBlock;
|
&bs->prevCBlock, &bs->nextCBlock);
|
||||||
bs->nextCBlock = tmp;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Writes the block header */
|
/* Writes the block header */
|
||||||
|
|||||||
@@ -1095,6 +1095,18 @@ pub unsafe extern "C" fn ZSTD_rust_resetCompressedBlockState(
|
|||||||
block_state.entropy.fse.litlength_repeatMode = FSE_REPEAT_NONE;
|
block_state.entropy.fse.litlength_repeatMode = FSE_REPEAT_NONE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Swaps the two C-owned block-state pointers after a block is confirmed.
|
||||||
|
///
|
||||||
|
/// The enclosing `ZSTD_blockState_t` contains C-only match-state storage, so
|
||||||
|
/// the ABI deliberately passes only the two pointer fields separately.
|
||||||
|
#[no_mangle]
|
||||||
|
pub unsafe extern "C" fn ZSTD_rust_confirmRepcodesAndEntropyTables(
|
||||||
|
prev_c_block: *mut *mut ZSTD_compressedBlockState_t,
|
||||||
|
next_c_block: *mut *mut ZSTD_compressedBlockState_t,
|
||||||
|
) {
|
||||||
|
unsafe { ptr::swap(prev_c_block, next_c_block) };
|
||||||
|
}
|
||||||
|
|
||||||
/// Appends the final literals of a block to its sequence store.
|
/// Appends the final literals of a block to its sequence store.
|
||||||
///
|
///
|
||||||
/// The source and destination ranges must be valid and non-overlapping, as
|
/// The source and destination ranges must be valid and non-overlapping, as
|
||||||
@@ -3258,6 +3270,23 @@ mod tests {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn confirm_repcodes_and_entropy_tables_swaps_block_state_pointers() {
|
||||||
|
let mut previous_storage = std::mem::MaybeUninit::<ZSTD_compressedBlockState_t>::uninit();
|
||||||
|
let mut next_storage = std::mem::MaybeUninit::<ZSTD_compressedBlockState_t>::uninit();
|
||||||
|
let previous = previous_storage.as_mut_ptr();
|
||||||
|
let next = next_storage.as_mut_ptr();
|
||||||
|
let mut previous_ptr = previous;
|
||||||
|
let mut next_ptr = next;
|
||||||
|
|
||||||
|
unsafe {
|
||||||
|
ZSTD_rust_confirmRepcodesAndEntropyTables(&mut previous_ptr, &mut next_ptr);
|
||||||
|
}
|
||||||
|
|
||||||
|
assert_eq!(previous_ptr, next);
|
||||||
|
assert_eq!(next_ptr, previous);
|
||||||
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn store_last_literals_copies_bytes_and_advances_only_the_literal_cursor() {
|
fn store_last_literals_copies_bytes_and_advances_only_the_literal_cursor() {
|
||||||
let mut sequences = [SeqDef::default(); 2];
|
let mut sequences = [SeqDef::default(); 2];
|
||||||
|
|||||||
Reference in New Issue
Block a user