Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

decompress a .lz4 file? #158

Open
jtmoon79 opened this issue May 5, 2024 · 3 comments
Open

decompress a .lz4 file? #158

jtmoon79 opened this issue May 5, 2024 · 3 comments

Comments

@jtmoon79
Copy link

jtmoon79 commented May 5, 2024

I'm trying to use lz4_flex to decompress a small .lz4 file. The file was compressed using lz4c on Ubuntu 22.

$ echo foobar > file

$ lz4c -9kv file
*** LZ4 command line interface 64-bits v1.9.3, by Yann Collet ***
Compressed filename will be : file.lz4
Compressed 7 bytes into 26 bytes ==> 371.43%

However, my various attempts at reading the file file.lz4 using a lz4_flex::frame::FrameDecoder and calls to .read or .read_exact do return Ok. However they do not appear to write anything to the passed Vec<u8>.

My code is

use std::fs::File;
use std::fs::OpenOptions;
use std::io::prelude::Read;
use std::io::BufReader;
use std::path::Path;
use ::lz4_flex;

fn main() {

    let mut open_options = OpenOptions::new();
    let path = String::from("/tmp/file.lz4");
    let path_std = Path::new(&path);
    let file_lz: File = match open_options.read(true).open(path_std) {
        Ok(val) => val,
        Err(err) => panic!("{}", err),
    };
    let mut bufreader = BufReader::<File>::new(file_lz);
    let mut lz4_decoder = lz4_flex::frame::FrameDecoder::new(bufreader);
    let mut buffer = Vec::<u8>::with_capacity(1024);
    let sz = match lz4_decoder.read(&mut buffer) {
    //match lz4_decoder.read_exact(&mut buffer) {
        Ok(_) => {}
        Err(err) => panic!("{}", err),
    };
    eprintln!("buffer: {:?}", buffer);
}

Could you provide an example for decompressing an .lz4 file?
Reviewing the examples, it was not obvious to me how to go about this as the examples only use "live" stdin streaming.

@PSeitz
Copy link
Owner

PSeitz commented May 6, 2024

Can you retry using std::io::copy like in the examples instead of a single read call?
https://docs.rs/lz4_flex/latest/lz4_flex/#example-decompress-data-on-stdin-with-frame-format

@jtmoon79
Copy link
Author

jtmoon79 commented May 6, 2024

Thanks @PSeitz . I got this working. I was not setting the length of the passed buffer (see rust-lang/rust#96915).

This code works (notice the call to resize)

use std::fs::File;
use std::fs::OpenOptions;
use std::io::prelude::Read;
use std::io::BufReader;
use std::path::Path;
use ::lz4_flex;

fn main() {
    let mut open_options = OpenOptions::new();
    let path = String::from("/tmp/file.lz4");
    let path_std = Path::new(&path);
    let file_lz: File = match open_options.read(true).open(path_std) {
        Ok(val) => val,
        Err(err) => panic!("{}", err),
    };
    let bufreader = BufReader::<File>::new(file_lz);
    let mut lz4_decoder = lz4_flex::frame::FrameDecoder::new(bufreader);
    let mut buffer = Vec::<u8>::with_capacity(1024);
    buffer.resize(1024, 0);
    let sz = match lz4_decoder.read(&mut buffer) {
        Ok(sz) => sz,
        Err(err) => panic!("{}", err),
    };
    eprintln!("buffer: {:?}", &buffer[..sz]);
}

If you're interested, I can submit a PR for this at /examples/decompress_file.rs.

@PSeitz
Copy link
Owner

PSeitz commented May 10, 2024

Yeah a PR would be nice, e.g. /examples/decompress_file_into_vec.rs

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants