Crate bsdiff_android

Crate bsdiff_android 

Source
Expand description

§bsdiff-android

GitHub crates.io version docs.rs docs CI build

Bsdiff/bspatch implementation with Android BSDF2 format support. Compatible with Android OTA payloads.

§Features

  • Classic bsdiff/bspatch (raw format)
  • BSDIFF40 format (BZ2 compressed, compatible with original tools)
  • Android BSDF2 format (Brotli/BZ2/None compression)
  • Fast suffix array construction

§Usage Examples

use bsdiff_android as bsdiff;

fn main() {
    let old = vec![1, 2, 3, 4, 5];
    let new = vec![1, 2, 4, 6];
    let mut patch = Vec::new();

    // Generate and apply patch
    bsdiff::diff(&old, &new, &mut patch).unwrap();
    
    let mut patched = Vec::new();
    bsdiff::patch(&old, &mut patch.as_slice(), &mut patched).unwrap();
    assert_eq!(patched, new);
}

§Classic BSDIFF40 Format

use bsdiff_android::{diff_bsdiff40, patch};

// Generate BSDIFF40 patch (compatible with original bsdiff tools)
let mut patch = Vec::new();
diff_bsdiff40(&old, &new, &mut patch)?;

// Apply patch
let mut result = Vec::new();
patch(&old, &mut patch.as_slice(), &mut result)?;

§Android BSDF2 Format (OTA Updates)

use bsdiff_android::{diff_bsdf2_uniform, patch_bsdf2, CompressionAlgorithm};

// Generate BSDF2 patch with Brotli compression (Android standard)
let mut patch = Vec::new();
diff_bsdf2_uniform(&old, &new, &mut patch, CompressionAlgorithm::Brotli)?;

// Apply BSDF2 patch
let mut result = Vec::new();
patch_bsdf2(&old, &patch, &mut result)?;

§File Operations

use bsdiff_android::{diff_bsdf2_uniform, patch_bsdf2, CompressionAlgorithm};
use std::fs;

fn create_update_package() -> std::io::Result<()> {
    // Read old and new versions
    let old = fs::read("app-v1.apk")?;
    let new = fs::read("app-v2.apk")?;
    
    // Generate Android OTA patch
    let mut patch = Vec::new();
    diff_bsdf2_uniform(&old, &new, &mut patch, CompressionAlgorithm::Brotli)?;
    fs::write("update.bsdf2", &patch)?;
    
    println!("Patch size: {} bytes", patch.len());
    Ok(())
}

fn apply_update() -> std::io::Result<()> {
    let old = fs::read("app-v1.apk")?;
    let patch = fs::read("update.bsdf2")?;
    
    let mut new = Vec::new();
    patch_bsdf2(&old, &patch, &mut new)?;
    fs::write("app-v2.apk", &new)?;
    
    Ok(())
}

§Mixed Compression (Advanced)

use bsdiff_android::{diff_bsdf2, CompressionAlgorithm};

// Use different compression for each stream
let mut patch = Vec::new();
diff_bsdf2(
    &old,
    &new,
    &mut patch,
    CompressionAlgorithm::Brotli,  // Control stream
    CompressionAlgorithm::Brotli,  // Diff stream  
    CompressionAlgorithm::Bz2,     // Extra stream
)?;

§API Summary

Use CaseGenerationApplication
Raw formatdiff()patch()
Classic BSDIFF40diff_bsdiff40()patch()
Android BSDF2diff_bsdf2_uniform()patch_bsdf2()

§Compression Types

CompressionAlgorithm::None    // No compression
CompressionAlgorithm::Bz2     // BZ2 compression
CompressionAlgorithm::Brotli  // Brotli (recommended for Android)

§License

BSD-2-Clause

Based on Colin Percival’s bsdiff/bspatch algorithm with Android BSDF2 extensions.

Structs§

Bsdf2Writer
BSDF2 patch writer
ControlEntry
Control entry matching

Enums§

CompressionAlgorithm

Functions§

apply_bsdf2_patch
Apply a BSDF2 patch with full validation and optimizations
apply_patch
Apply a patch to an “old” file, returning the “new” file.
diff
Diff an “old” and a “new” file, returning a legacy BSDIFF40 patch.
diff_bsdf2
Generate a BSDF2 patch with specified compression algorithms
diff_bsdf2_uniform
Generate a BSDF2 patch with all streams using the same compression
diff_bsdiff40
Generate a legacy BSDIFF40 patch (BZ2 compressed)
parse_bsdf2_header
Parse BSDF2 or classic BSDIFF patch header and return streams
patch
Apply a patch to an “old” file, returning the “new” file.
patch_bsdf2
Apply a BSDF2 patch with full validation and optimizations