Skip to content
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 5 additions & 3 deletions src/db/car/any.rs
Original file line number Diff line number Diff line change
Expand Up @@ -34,8 +34,10 @@ impl<ReaderT: RandomAccessFileReader> AnyCar<ReaderT> {
/// `.forest.car.zst`. This call may block for an indeterminate amount of
/// time while data is decoded and indexed.
pub fn new(reader: ReaderT) -> Result<Self> {
if super::ForestCar::is_valid(&reader) {
return Ok(AnyCar::Forest(super::ForestCar::new(reader)?));
if let Ok(validation_result) = super::ForestCar::validate_car(&reader) {
return Ok(
super::ForestCar::new_from_validation_result(reader, validation_result)?.into(),
);
}

// Maybe use a tempfile for this in the future.
Expand All @@ -46,7 +48,7 @@ impl<ReaderT: RandomAccessFileReader> AnyCar<ReaderT> {
}

if let Ok(plain_car) = super::PlainCar::new(reader) {
return Ok(AnyCar::Plain(plain_car));
return Ok(plain_car.into());
}
Err(Error::new(
ErrorKind::InvalidData,
Expand Down
11 changes: 9 additions & 2 deletions src/db/car/forest.rs
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,14 @@ pub struct ForestCar<ReaderT> {

impl<ReaderT: super::RandomAccessFileReader> ForestCar<ReaderT> {
pub fn new(reader: ReaderT) -> io::Result<ForestCar<ReaderT>> {
let (header, index_start_pos, index_size_bytes) = Self::validate_car(&reader)?;
let validation_result = Self::validate_car(&reader)?;
Self::new_from_validation_result(reader, validation_result)
}

pub(super) fn new_from_validation_result(
reader: ReaderT,
(header, index_start_pos, index_size_bytes): (CarV1Header, u64, u64),
) -> io::Result<ForestCar<ReaderT>> {
let indexed = index::Reader::new(index::ZstdSkipFramesEncodedDataReader::new(
positioned_io::Slice::new(reader, index_start_pos, Some(index_size_bytes)),
)?)?;
Expand Down Expand Up @@ -138,7 +145,7 @@ impl<ReaderT: super::RandomAccessFileReader> ForestCar<ReaderT> {
Self::validate_car(reader).is_ok()
}

fn validate_car(reader: &ReaderT) -> io::Result<(CarV1Header, u64, u64)> {
pub(super) fn validate_car(reader: &ReaderT) -> io::Result<(CarV1Header, u64, u64)> {
let mut cursor = SizeCursor::new(&reader);
cursor.seek(SeekFrom::End(-(ForestCarFooter::SIZE as i64)))?;
let index_end_pos = cursor.position();
Expand Down
13 changes: 11 additions & 2 deletions src/db/car/many.rs
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@ use fvm_ipld_blockstore::Blockstore;
use parking_lot::RwLock;
use std::cmp::Ord;
use std::collections::BinaryHeap;
use std::path::Path;
use std::{path::PathBuf, sync::Arc};

struct WithHeaviestEpoch {
Expand Down Expand Up @@ -124,12 +125,20 @@ impl<WriterT> ManyCar<WriterT> {

pub fn read_only_files(&self, files: impl Iterator<Item = PathBuf>) -> anyhow::Result<()> {
for file in files {
self.read_only(AnyCar::new(EitherMmapOrRandomAccessFile::open(file)?)?)?;
self.read_only_file(file)?;
}

Ok(())
}

pub fn read_only_file(&self, file: impl AsRef<Path>) -> anyhow::Result<()> {
(|| {
self.read_only(AnyCar::new(EitherMmapOrRandomAccessFile::open(
file.as_ref(),
)?)?)
})()
.map_err(|e| anyhow::anyhow!("failed to load CAR at {}: {e}", file.as_ref().display()))
}

pub fn heaviest_tipset_key(&self) -> anyhow::Result<Option<TipsetKey>> {
Ok(self
.read_only
Expand Down
Loading