fix segmentation fault
add read_block function to reader
This commit is contained in:
@@ -3,6 +3,7 @@ use std::str;
|
||||
use std::ffi::CStr;
|
||||
|
||||
use libarchive3_sys::ffi;
|
||||
use error::ErrCode;
|
||||
|
||||
pub enum ReadCompression {
|
||||
All,
|
||||
@@ -93,8 +94,9 @@ pub enum WriteFilter {
|
||||
pub trait Handle {
|
||||
unsafe fn handle(&self) -> *mut ffi::Struct_archive;
|
||||
|
||||
fn err_code(&self) -> i32 {
|
||||
unsafe { ffi::archive_errno(self.handle()) }
|
||||
fn err_code(&self) -> ErrCode {
|
||||
let code = unsafe { ffi::archive_errno(self.handle()) };
|
||||
ErrCode(code)
|
||||
}
|
||||
|
||||
fn err_msg(&self) -> String {
|
||||
|
||||
@@ -5,7 +5,7 @@ use archive;
|
||||
pub type ArchiveResult<T> = Result<T, ArchiveError>;
|
||||
|
||||
#[derive(Debug)]
|
||||
pub struct ErrCode(i32);
|
||||
pub struct ErrCode(pub i32);
|
||||
|
||||
impl fmt::Display for ErrCode {
|
||||
fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
|
||||
@@ -44,20 +44,14 @@ impl fmt::Display for ArchiveError {
|
||||
|
||||
impl<'a> From<&'a archive::Handle> for ArchiveError {
|
||||
fn from(handle: &'a archive::Handle) -> ArchiveError {
|
||||
ArchiveError::Sys(ErrCode::from(handle), handle.err_msg())
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> From<&'a archive::Handle> for ErrCode {
|
||||
fn from(handle: &'a archive::Handle) -> ErrCode {
|
||||
ErrCode(handle.err_code())
|
||||
ArchiveError::Sys(handle.err_code(), handle.err_msg())
|
||||
}
|
||||
}
|
||||
|
||||
impl<'a> From<&'a archive::Handle> for ArchiveResult<()> {
|
||||
fn from(handle: &'a archive::Handle) -> ArchiveResult<()> {
|
||||
match handle.err_code() {
|
||||
0 => Ok(()),
|
||||
ErrCode(0) => Ok(()),
|
||||
_ => Err(ArchiveError::from(handle)),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@ use std::io::{self, Read};
|
||||
use std::mem;
|
||||
use std::path::Path;
|
||||
use std::ptr;
|
||||
use std::slice;
|
||||
|
||||
use libc::{c_void, ssize_t};
|
||||
use libarchive3_sys::ffi;
|
||||
@@ -38,7 +39,7 @@ pub trait Reader : Handle {
|
||||
unsafe { ffi::archive_read_header_position(self.handle()) }
|
||||
}
|
||||
|
||||
fn next_header(&mut self) -> Option<&ReaderEntry> {
|
||||
fn next_header(&mut self) -> Option<&mut ReaderEntry> {
|
||||
let res = unsafe { ffi::archive_read_next_header(self.handle(), &mut self.entry().handle) };
|
||||
if res == 0 {
|
||||
Some(self.entry())
|
||||
@@ -46,6 +47,20 @@ pub trait Reader : Handle {
|
||||
None
|
||||
}
|
||||
}
|
||||
|
||||
fn read_block(&self) -> ArchiveResult<Option<&[u8]>> {
|
||||
let mut buff = ptr::null();
|
||||
let mut size = 0;
|
||||
let mut offset = 0;
|
||||
|
||||
unsafe {
|
||||
match ffi::archive_read_data_block(self.handle(), &mut buff, &mut size, &mut offset) {
|
||||
ffi::ARCHIVE_EOF => Ok(None),
|
||||
ffi::ARCHIVE_OK => Ok(Some(slice::from_raw_parts(buff as *const u8, size))),
|
||||
_ => Err(ArchiveError::Sys(self.err_code(), self.err_msg())),
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub struct FileReader {
|
||||
@@ -56,7 +71,7 @@ pub struct FileReader {
|
||||
pub struct StreamReader {
|
||||
handle: *mut ffi::Struct_archive,
|
||||
entry: ReaderEntry,
|
||||
_pipe: Pipe,
|
||||
_pipe: Box<Pipe>,
|
||||
}
|
||||
|
||||
pub struct Builder {
|
||||
@@ -133,9 +148,8 @@ impl Drop for FileReader {
|
||||
impl StreamReader {
|
||||
pub fn open<T: Any + Read>(mut builder: Builder, src: T) -> ArchiveResult<Self> {
|
||||
unsafe {
|
||||
builder.consume();
|
||||
let mut pipe = Pipe::new(src);
|
||||
let pipe_ptr: *mut c_void = &mut pipe as *mut Pipe as *mut c_void;
|
||||
let mut pipe = Box::new(Pipe::new(src));
|
||||
let pipe_ptr: *mut c_void = &mut *pipe as *mut Pipe as *mut c_void;
|
||||
match ffi::archive_read_open(builder.handle(),
|
||||
pipe_ptr,
|
||||
None,
|
||||
@@ -147,9 +161,13 @@ impl StreamReader {
|
||||
entry: ReaderEntry::default(),
|
||||
_pipe: pipe,
|
||||
};
|
||||
builder.consume();
|
||||
Ok(reader)
|
||||
}
|
||||
_ => Err(ArchiveError::from(&builder as &Handle)),
|
||||
_ => {
|
||||
builder.consume();
|
||||
Err(ArchiveError::from(&builder as &Handle))
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user