From 3f081ee53b2947a2fee7f66e94d1b7e74933a289 Mon Sep 17 00:00:00 2001 From: ddidderr Date: Mon, 20 Jul 2026 13:34:20 +0200 Subject: [PATCH] refactor(compress): export context parameter policy from Rust Move ZSTD_getCParamsFromCCtxParams() out of its C forwarding body and export the original symbol from the Rust parameter API. The Rust-side ABI mirror already has layout checks, so it can project the same fields to the existing scalar policy leaf without exposing additional context state. Keep the exclusion mask in C and query it from Rust so reduced builds retain their preprocessor-selected block-compressor behavior. Test Plan: - `cc -fsyntax-only -Ilib -Ilib/common -Ilib/compress -Ilib/decompress -Ilib/dict -Ilib/legacy lib/compress/zstd_compress.c` -- passed. - `cargo +nightly fmt --manifest-path rust/Cargo.toml --all -- --check` -- passed. - `git diff --check` and `git diff --cached --check` -- passed. - Heavy Cargo, Make, native, and test-suite verification intentionally not run per request. --- lib/compress/zstd_compress.c | 12 +---- rust/src/zstd_compress_params_api.rs | 73 ++++++++++++++++++++++++++++ 2 files changed, 74 insertions(+), 11 deletions(-) diff --git a/lib/compress/zstd_compress.c b/lib/compress/zstd_compress.c index b17de4cb0..1c9d6846f 100644 --- a/lib/compress/zstd_compress.c +++ b/lib/compress/zstd_compress.c @@ -3924,17 +3924,7 @@ U32 ZSTD_getCParamsExclusionMask(void) return mask; } -ZSTD_compressionParameters ZSTD_getCParamsFromCCtxParams( - const ZSTD_CCtx_params* CCtxParams, U64 srcSizeHint, size_t dictSize, ZSTD_CParamMode_e mode) -{ - return ZSTD_rust_params_getCParamsFromCCtxParams( - CCtxParams->compressionLevel, CCtxParams->srcSizeHint, - srcSizeHint, dictSize, (int)mode, - (int)CCtxParams->ldmParams.enableLdm, - ZSTD_LDM_DEFAULT_WINDOW_LOG, CCtxParams->cParams, - (int)CCtxParams->useRowMatchFinder, - ZSTD_getCParamsExclusionMask()); -} +/* ZSTD_getCParamsFromCCtxParams() is implemented directly by Rust. */ static size_t ZSTD_estimateCCtxSize_usingCCtxParams_internal( const ZSTD_compressionParameters* cParams, diff --git a/rust/src/zstd_compress_params_api.rs b/rust/src/zstd_compress_params_api.rs index 510607655..7afb83e9a 100644 --- a/rust/src/zstd_compress_params_api.rs +++ b/rust/src/zstd_compress_params_api.rs @@ -129,6 +129,7 @@ pub struct ZSTD_CCtx_params { const DEFAULT_CLEVEL: c_int = 3; const NO_CLEVEL: c_int = 0; +const ZSTD_LDM_DEFAULT_WINDOW_LOG: u32 = 27; const PS_AUTO: c_int = 0; const PS_DISABLE: c_int = 2; @@ -204,12 +205,23 @@ pub extern "C" fn ZSTD_rust_isUpdateAuthorized(param: c_int) -> c_int { #[cfg(not(test))] unsafe extern "C" { + fn ZSTD_getCParamsExclusionMask() -> u32; fn ZSTD_rust_cctx_params_is_multithreaded() -> c_int; fn ZSTD_rust_cctx_params_nb_workers_max() -> c_int; fn ZSTD_rust_cctx_params_job_size_min() -> c_int; fn ZSTD_rust_cctx_params_job_size_max() -> c_int; } +#[cfg(not(test))] +fn cparams_exclusion_mask() -> u32 { + unsafe { ZSTD_getCParamsExclusionMask() } +} + +#[cfg(test)] +fn cparams_exclusion_mask() -> u32 { + 0 +} + #[derive(Clone, Copy)] struct BoundsConfig { multithreaded: bool, @@ -582,6 +594,34 @@ pub unsafe extern "C" fn ZSTD_rust_CCtxParams_setZstdParams( unsafe { set_zstd_params_impl(cctx_params, zstd_params) } } +/// Rust implementation of the private `ZSTD_getCParamsFromCCtxParams()` +/// policy leaf. +/// +/// The `ZSTD_CCtx_params` mirror is layout-checked in this module. The +/// exclusion mask remains supplied by C so build-time block-compressor +/// configuration continues to follow the C preprocessor configuration. +#[no_mangle] +pub unsafe extern "C" fn ZSTD_getCParamsFromCCtxParams( + cctx_params: *const ZSTD_CCtx_params, + src_size_hint: u64, + dict_size: usize, + mode: c_int, +) -> ZSTD_compressionParameters { + let cctx_params = unsafe { &*cctx_params }; + ZSTD_rust_params_getCParamsFromCCtxParams( + cctx_params.compressionLevel, + cctx_params.srcSizeHint, + src_size_hint, + dict_size, + mode, + cctx_params.ldmParams.enableLdm, + ZSTD_LDM_DEFAULT_WINDOW_LOG, + cctx_params.cParams, + cctx_params.useRowMatchFinder, + cparams_exclusion_mask(), + ) +} + /// Prepares the parameter subset used by `ZSTD_createCDict_advanced2()`. /// /// The C dictionary allocator remains responsible for allocation and @@ -1334,6 +1374,39 @@ mod tests { ); } + #[test] + fn direct_cparams_projection_matches_the_scalar_policy_leaf() { + let mut storage = MaybeUninit::::zeroed(); + let params = storage.as_mut_ptr(); + + unsafe { + assert_eq!(ZSTD_CCtxParams_init(params, DEFAULT_CLEVEL), 0); + (*params).srcSizeHint = 16 * 1024; + + let expected = ZSTD_rust_params_getCParamsFromCCtxParams( + (*params).compressionLevel, + (*params).srcSizeHint, + ZSTD_CONTENTSIZE_UNKNOWN, + 0, + ZSTD_RUST_CPM_NO_ATTACH_DICT, + (*params).ldmParams.enableLdm, + ZSTD_LDM_DEFAULT_WINDOW_LOG, + (*params).cParams, + (*params).useRowMatchFinder, + 0, + ); + assert_eq!( + ZSTD_getCParamsFromCCtxParams( + params, + ZSTD_CONTENTSIZE_UNKNOWN, + 0, + ZSTD_RUST_CPM_NO_ATTACH_DICT, + ), + expected + ); + } + } + #[test] fn target_c_block_size_predicate_uses_zero_as_the_disable_value() { let mut storage = MaybeUninit::::zeroed();