use chrono::prelude::DateTime;
use log::{debug, error};
use std::fs::File;
use std::io::Read;
pub fn read_file(file: impl Into<String>) -> Result<Vec<u8>, std::io::Error> {
let mut file_data = Vec::new();
let file_path = file.into();
match File::open(&file_path) {
Err(e) => {
error!("Failed to open file {}: {}", file_path, e);
Err(e)
}
Ok(mut fp) => match fp.read_to_end(&mut file_data) {
Err(e) => {
error!("Failed to read file {} into memory: {}", file_path, e);
Err(e)
}
Ok(file_size) => {
debug!("Loaded {} bytes from {}", file_size, file_path);
Ok(file_data)
}
},
}
}
pub fn crc32(data: &[u8]) -> u32 {
crc32_v2::crc32(0, data)
}
pub fn epoch_to_string(epoch_timestamp: u32) -> String {
let date_time = DateTime::from_timestamp(epoch_timestamp.into(), 0);
match date_time {
Some(dt) => dt.format("%Y-%m-%d %H:%M:%S").to_string(),
None => "".to_string(),
}
}
fn get_cstring_bytes(raw_data: &[u8]) -> Vec<u8> {
let mut cstring: Vec<u8> = vec![];
for raw_byte in raw_data {
if *raw_byte == 0 {
break;
} else {
cstring.push(*raw_byte);
}
}
cstring
}
pub fn get_cstring(raw_data: &[u8]) -> String {
let raw_string = get_cstring_bytes(raw_data);
let string: String = match String::from_utf8(raw_string) {
Err(_) => "".to_string(),
Ok(s) => s.clone(),
};
string
}
pub fn is_offset_safe(
available_data: usize,
next_offset: usize,
last_offset: Option<usize>,
) -> bool {
if let Some(previous_offset) = last_offset {
if previous_offset >= next_offset {
return false;
}
}
if next_offset >= available_data {
return false;
}
true
}