summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/object.rs33
1 files changed, 18 insertions, 15 deletions
diff --git a/src/object.rs b/src/object.rs
index 5824c47..c4edcbd 100644
--- a/src/object.rs
+++ b/src/object.rs
@@ -1,8 +1,8 @@
+use crate::die;
+use flate2::read::ZlibDecoder;
use std::fs::File;
-use std::io::{BufReader, Read};
+use std::io::Read;
use std::path::PathBuf;
-use flate2::read::ZlibDecoder;
-use crate::die;
pub enum GitObjectType {
Blob,
@@ -12,7 +12,7 @@ pub enum GitObjectType {
Undefined,
}
-struct GitObject {
+pub struct GitObject {
object_type: GitObjectType,
size: usize,
data: Vec<u8>,
@@ -27,42 +27,42 @@ impl GitObject {
}
}
- fn from_file(path: PathBuf) -> Self {
+ pub fn from_file(path: PathBuf) -> Self {
if !path.is_file() {
return Self::new();
}
if let Ok(compressed_content) = File::open(path.clone()) {
let sha = path.file_name().unwrap().to_str().unwrap();
- let decoder = ZlibDecoder::new(BufReader::new(compressed_content));
- let mut reader = ZlibDecoder::new(decoder);
+ let mut decoder = ZlibDecoder::new(compressed_content);
+ let mut decompressed = Vec::new();
+ decoder.read_to_end(&mut decompressed).unwrap();
let mut type_buffer = Vec::new();
let mut size_buffer = Vec::new();
let mut data = Vec::new();
- let mut byte = [0u8; 1];
let mut current_segment: u8 = 0; // 0: type, 1: size, 2: content
- while reader.read_exact(&mut byte).is_ok() {
+ decompressed.iter().for_each(|&byte| {
match current_segment {
0 => {
- if byte[0] != b' ' {
- type_buffer.push(byte[0]);
+ if byte != b' ' {
+ type_buffer.push(byte);
} else {
current_segment += 1;
}
}
1 => {
- if byte[0] == b'\x00' {
- size_buffer.push(byte[0]);
+ if byte != 0 {
+ size_buffer.push(byte);
} else {
current_segment += 1;
}
}
_ => {
- data.push(byte[0]);
+ data.push(byte);
}
}
- }
+ });
let object_type = match String::from_utf8_lossy(&type_buffer).to_string().as_str() {
"commit" => { GitObjectType::Commit }
"tree" => { GitObjectType::Tree }
@@ -79,6 +79,9 @@ impl GitObject {
let Ok(size) = String::from_utf8_lossy(&size_buffer).to_string().parse::<usize>() else {
die!("Malformed object {}, unknown size", sha);
};
+ if data.len() != size {
+ die!("Malformed object {}, size doesn't match", sha, size);
+ }
Self {
object_type,
size,