oxiarc-deflate [Stable]
Pure Rust implementation of the DEFLATE compression algorithm (RFC 1951).
Version 0.3.1 (2026-05-30) — 212 tests passing.
What's new in 0.3.x (latest):
- Parallel GZIP compression (
parallelfeature): pigz-style multi-member GZIP viagzip_compress_parallel()andParallelGzipEncoderbuilder. - LZ77 match heuristics tuning:
Lz77Params/Lz77Presetstructs andDeflater::with_lz77_params()/Deflater::with_lz77_preset()builder methods for fine-grained speed/ratio trade-offs. - DeflatePool memory pool:
DeflatePoolfor thread-safe window/hash buffer reuse withDeflater::with_pool()andPoolStatstracking. - OptimalParser: Zopfli-style graph-based optimal DEFLATE parsing strategy. Enable via
Deflater::with_optimal_parsing(level).
What's new in 0.2.8: Added async streaming support for raw DEFLATE with RawDeflateWriter and RawInflateReader (requires async-io feature).
What's new in 0.2.6: Added streaming support with GzipStreamEncoder/GzipStreamDecoder and ZlibStreamEncoder/ZlibStreamDecoder with flush modes for fine-grained control over compressed output.
Overview
DEFLATE is the compression algorithm used in:
- ZIP archives
- GZIP compressed files
- PNG images
- HTTP compression
- Many other formats
This crate provides both compression and decompression with no external dependencies.
Features
- Pure Rust - No C bindings or unsafe code
- Full RFC 1951 compliance - All block types supported
- Compression levels 0-9 - From stored to maximum compression
- Streaming API - Process data in chunks
- One-shot API - Convenient functions for simple cases
- Async I/O -
async_deflatemodule with Tokio-based async streaming (enableasync-iofeature) - GZIP support -
gzipmodule for RFC 1952 GZIP format encoding/decoding - Parallel GZIP compression - pigz-style multi-member GZIP using multiple threads (enable
parallelfeature) - LZ77 heuristics tuning -
Lz77Params/Lz77Presetfor speed/ratio trade-off control - Memory pool -
DeflatePoolfor reusing window/hash buffers across compression calls
All features are implemented and tested. API is stable.
Cargo Features
| Feature | Default | Description |
|---|---|---|
default |
yes | DEFLATE compression/decompression, LZ77, Huffman, OptimalParser, LZ77 heuristics, DeflatePool |
async-io |
no | Async streaming I/O via Tokio (enables async_deflate module) |
parallel |
no | Multi-threaded GZIP compression via gzip_compress_parallel and ParallelGzipEncoder |
Usage
Add to your Cargo.toml:
[]
= "0.3.1"
With async I/O support:
[]
= { = "0.3.1", = ["async-io"] }
With parallel GZIP compression:
[]
= { = "0.3.1", = ["parallel"] }
Quick Start
use ;
// Compress data
let original = b"Hello, World! Hello, World! Hello, World!";
let compressed = deflate?; // Level 6 (default)
// Decompress data
let decompressed = inflate?;
assert_eq!;
Compression Levels
| Level | Description | Use Case |
|---|---|---|
| 0 | Stored (no compression) | Already compressed data |
| 1-3 | Fast compression | Real-time streaming |
| 4-6 | Balanced (default: 6) | General purpose |
| 7-9 | Best compression | Archival, storage |
API
High-Level Functions
// Compress with specified level
let compressed = deflate?;
// Decompress
let decompressed = inflate?;
Streaming API
use ;
// Streaming compression
let mut deflater = new;
let compressed = deflater.compress_all?;
// Streaming decompression
let mut inflater = new;
loop
LZ77 Encoder
use ;
let mut encoder = new;
for token in encoder.encode
Huffman Trees
use ;
// Build tree from code lengths
let lengths = ;
let tree = from_lengths?;
// Decode symbols
let symbol = tree.decode?;
Algorithm Details
DEFLATE Structure
+------------------+
| Block Header | (3 bits: BFINAL + BTYPE)
+------------------+
| Block Data | (varies by type)
+------------------+
| ... more blocks |
+------------------+
Block Types
| BTYPE | Name | Description |
|---|---|---|
| 00 | Stored | Uncompressed data (up to 65535 bytes) |
| 01 | Fixed | Fixed Huffman codes (RFC 1951 Table) |
| 10 | Dynamic | Custom Huffman codes in header |
| 11 | Reserved | Invalid |
LZ77 Parameters
- Window size: 32768 bytes (32KB)
- Match length: 3-258 bytes
- Match distance: 1-32768 bytes
- Minimum match: 3 bytes
Huffman Alphabets
Literal/Length (286 symbols):
- 0-255: Literal bytes
- 256: End of block
- 257-285: Length codes (3-258)
Distance (30 symbols):
- 0-29: Distance codes (1-32768)
Fixed Huffman Code Lengths
| Range | Code Length |
|---|---|
| 0-143 | 8 bits |
| 144-255 | 9 bits |
| 256-279 | 7 bits |
| 280-287 | 8 bits |
Modules
| Module | Description |
|---|---|
deflate |
Compression (encoder) |
inflate |
Decompression (decoder) |
huffman |
Huffman tree operations |
lz77 |
LZ77 dictionary encoder; Lz77Params, Lz77Preset |
tables |
Fixed Huffman tables, length/distance extra bits |
gzip |
GZIP format (RFC 1952) encoding, decoding, and parallel compression |
pool |
DeflatePool and PoolStats for window/hash buffer reuse |
async_deflate |
Async streaming compression/decompression (requires async-io feature) |
GZIP API
use ;
// Encode to GZIP format
let compressed = gzip_encode?;
// Decode GZIP data
let decompressed = gzip_decode?;
Async DEFLATE (requires async-io feature)
use ;
use BufReader;
// Async compression
let mut deflater = new;
let compressed = deflater.compress_all.await?;
// Async decompression
let mut inflater = new;
let decompressed = inflater.decompress_all.await?;
Parallel GZIP (requires parallel feature)
use ;
// One-shot parallel GZIP (pigz-style multi-member output)
let compressed = gzip_compress_parallel?; // level 6, 128 KB chunks
// Builder API
let compressed = new
.level
.chunk_size // 128 KB per chunk
.num_threads
.encode?;
LZ77 Heuristics Tuning
use ;
// Use a preset
let compressed = new
.with_lz77_preset
.compress_all?;
// Fine-grained control
let params = Lz77Params ;
let compressed = new
.with_lz77_params
.compress_all?;
Available presets:
| Preset | Description |
|---|---|
Fast |
Minimal chain searching, fastest throughput |
Default |
Balanced speed and ratio (equivalent to level 6) |
Best |
Longer chain searching, best standard ratio |
Ultra |
Maximum chain searching, slowest but smallest output |
DeflatePool (memory pool)
use ;
// Create a shared pool (e.g., once per application / thread pool)
let pool = new;
// Reuse window/hash buffers across calls — reduces allocations
let compressed = new
.with_pool
.compress_all?;
// Inspect pool statistics
let stats = pool.stats;
println!;
Performance
Compression ratios on typical data (Calgary Corpus):
| File | Original | Compressed | Ratio |
|---|---|---|---|
| book1 | 768771 | ~300000 | ~61% |
| paper1 | 53161 | ~18000 | ~66% |
| progc | 39611 | ~13000 | ~67% |
References
License
Apache-2.0