From ae6b33a760e923ab5376ff7fc86f893de99b03e2 Mon Sep 17 00:00:00 2001 From: Simon Renblad Date: Tue, 30 Jul 2024 17:35:30 +0800 Subject: [PATCH] some WIP exploration --- libconfig/src/bootgen.rs | 13 ++++--- libconfig/src/lib.rs | 10 +++-- libconfig/src/sd_reader.rs | 77 +++++++++++++++++++++++++++----------- 3 files changed, 69 insertions(+), 31 deletions(-) diff --git a/libconfig/src/bootgen.rs b/libconfig/src/bootgen.rs index 884f22c..a2c1326 100644 --- a/libconfig/src/bootgen.rs +++ b/libconfig/src/bootgen.rs @@ -1,5 +1,7 @@ use alloc::vec::Vec; -use core_io::{Error, Read, Seek, SeekFrom}; +use fatfs::{Read, Seek, SeekFrom, IoBase}; +use core::fmt::Write; +use crate::sd_reader::IoError; use libboard_zynq::devc; use log::debug; @@ -8,12 +10,13 @@ pub enum BootgenLoadingError { InvalidBootImageHeader, MissingPartition, EncryptedBitstream, - IoError(Error), + IoError(IoError), DevcError(devc::DevcError), } -impl From for BootgenLoadingError { - fn from(error: Error) -> Self { + +impl From for BootgenLoadingError { + fn from(error: IoError) -> Self { BootgenLoadingError::IoError(error) } } @@ -69,7 +72,7 @@ fn read_u32(reader: &mut Reader) -> Result( +fn load_pl_header( file: &mut File, ) -> Result, BootgenLoadingError> { let mut buffer: [u8; 0x40] = [0; 0x40]; diff --git a/libconfig/src/lib.rs b/libconfig/src/lib.rs index cc958b9..c23b4e2 100644 --- a/libconfig/src/lib.rs +++ b/libconfig/src/lib.rs @@ -13,7 +13,7 @@ pub mod bootgen; #[derive(Debug)] pub enum Error<'a> { SdError(sdio::sd_card::CardInitializationError), - IoError(sd_reader::SdReader::Error), + IoError(fatfs::Error), Utf8Error(FromUtf8Error), KeyNotFoundError(&'a str), NoConfig, @@ -39,8 +39,8 @@ impl<'a> From for Error<'a> { } } -impl<'a> From for Error<'a> { - fn from(error: sd_reader::SdReader::Error) -> Self { +impl<'a> From> for Error<'a> { + fn from(error: fatfs::Error) -> Self { Error::IoError(error) } } @@ -51,10 +51,12 @@ impl<'a> From for Error<'a> { } } +pub type FFile = fatfs::File; + fn parse_config<'a>( key: &'a str, buffer: &mut Vec, - file: fatfs::File, + file: FFile, ) -> Result<'a, ()> { let prefix = [key, "="].concat().to_ascii_lowercase(); let file_buf = &mut []; diff --git a/libconfig/src/sd_reader.rs b/libconfig/src/sd_reader.rs index 5fc9254..3cecf83 100644 --- a/libconfig/src/sd_reader.rs +++ b/libconfig/src/sd_reader.rs @@ -1,4 +1,4 @@ -use fatfs::{self as fatfs, Read, Seek, SeekFrom, Write, IoBase}; +use fatfs::{self as fatfs, Read, Seek, SeekFrom, Write, IoBase, IoError as BaseIoError}; use libboard_zynq::sdio::{sd_card::SdCard, CmdTransferError}; use log::debug; use alloc::vec::Vec; @@ -15,6 +15,46 @@ const PARTID_FAT16_LBA: u8 = 0x0E; const BLOCK_SIZE: usize = 512; +#[derive(Debug)] +pub enum ErrorKind { + InvalidData, + InvalidInput, + Other +} + +#[derive(Debug)] +pub struct IoError { + error: ErrorKind, + message: String +} + +impl IoError { + pub fn new(error: ErrorKind, message: &str) -> Self { + IoError { + error, + message: String::from(message) + } + } +} + +impl BaseIoError for IoError { + fn is_interrupted() -> IoError { + false + } + fn new_unexpected_eof_error() -> IoError{ + + } + fn new_write_zero_error() -> IoError { + + } +} + +pub type IoResult = core::Result; + +fn cmd_error_to_io_error(_: CmdTransferError) -> IoError { + IoError::new(ErrorKind::Other, "Command transfer error") +} + /// SdReader struct implementing `Read + BufRead + Write + Seek` traits for `core_io`. /// Used as an adaptor for fatfs crate, but could be used directly for raw data access. /// @@ -51,7 +91,7 @@ pub enum PartitionEntry { } impl IoBase for SdReader { - type Error = fatfs::error::Error; + type Error = IoError; } impl SdReader { @@ -73,7 +113,7 @@ impl SdReader { /// Internal read function for unaligned read. /// The read must not cross block boundary. - fn read_unaligned(&mut self, buf: &mut [u8]) -> Result { + fn read_unaligned(&mut self, buf: &mut [u8]) -> IoResult { if buf.len() == 0 { return Ok(0); } @@ -87,7 +127,7 @@ impl SdReader { /// Internal write function for unaligned write. /// The write must not cross block boundary. - fn write_unaligned(&mut self, buf: &[u8]) -> Result { + fn write_unaligned(&mut self, buf: &[u8]) -> IoResult { if buf.len() == 0 { return Ok(0); } @@ -138,7 +178,7 @@ impl SdReader { } /// Set the base offset of the SD card, to transform from physical address to logical address. - fn set_base_offset(&mut self, offset: u32) -> Result { + fn set_base_offset(&mut self, offset: u32) -> IoResult { self.offset = offset; self.seek(SeekFrom::Start(0)) } @@ -146,16 +186,13 @@ impl SdReader { /// Mount fatfs from partition entry, and return the fatfs object if success. /// This takes the ownership of self, so currently there is no way to recover from an error, /// except creating a new SD card instance. - pub fn mount_fatfs(mut self, entry: PartitionEntry) -> Result, Self::Error> { + pub fn mount_fatfs(mut self, entry: PartitionEntry) -> IoResult> { let mut buffer: [u8; 4] = [0; 4]; self.seek(SeekFrom::Start(0x1FE))?; self.read_exact(&mut buffer[..2])?; // check MBR signature if buffer[..2] != MBR_SIGNATURE { - return Err(Self::Error::new( - ErrorKind::InvalidData, - "Incorrect signature for MBR sector.", - )); + return Err(IoError::new(ErrorKind::InvalidData, "Incorrect signature for MBR sector.")); } // Read partition ID. self.seek(SeekFrom::Start(entry as u64 + 0x4))?; @@ -165,9 +202,8 @@ impl SdReader { PARTID_FAT12 | PARTID_FAT16_LESS32M | PARTID_FAT16 | PARTID_FAT16_LBA | PARTID_FAT32 | PARTID_FAT32_LBA => {} _ => { - return Err(Self::Error::new( - ErrorKind::InvalidData, - "No FAT partition found for the specified entry.", + return Err(IoError::new(ErrorKind::InvalidData, + "No FAT partition found for the specified entry." )); } } @@ -185,10 +221,7 @@ impl SdReader { fatfs::FileSystem::new(self, fatfs::FsOptions::new()) } - fn cmd_error_to_io_error(_: CmdTransferError) -> Self::Error { - Self::Error::Other("Command transfer error") - } - fn fill_buf(&mut self) -> Result<&[u8], Self::Error> { + fn fill_buf(&mut self) -> IoResult<&[u8]> { if self.index == BLOCK_SIZE { // flush the buffer if it is dirty before overwriting it with new data if self.dirty { @@ -211,7 +244,7 @@ impl SdReader { impl Read for SdReader { - fn read(&mut self, buf: &mut [u8]) -> Result { + fn read(&mut self, buf: &mut [u8]) -> IoResult { let total_length = buf.len(); let (a, b, c) = self.block_align_mut(buf); self.read_unaligned(a)?; @@ -237,7 +270,7 @@ impl Read for SdReader { } impl Write for SdReader { - fn write(&mut self, buf: &[u8]) -> Result { + fn write(&mut self, buf: &[u8]) -> IoResult { let (a, b, c) = self.block_align(buf); self.write_unaligned(a)?; if b.len() > 0 { @@ -258,7 +291,7 @@ impl Write for SdReader { Ok(buf.len()) } - fn flush(&mut self) -> Result<(), Self::Error> { + fn flush(&mut self) -> IoResult<()> { if self.dirty { let block_addr = (self.byte_addr - self.index as u32) / (BLOCK_SIZE as u32); self.sd @@ -271,14 +304,14 @@ impl Write for SdReader { } impl Seek for SdReader { - fn seek(&mut self, pos: SeekFrom) -> Result { + fn seek(&mut self, pos: SeekFrom) -> IoResult { let raw_target = match pos { SeekFrom::Start(x) => self.offset as i64 + x as i64, SeekFrom::Current(x) => self.byte_addr as i64 + x, SeekFrom::End(_) => panic!("SD card does not support seek from end"), }; if raw_target < self.offset as i64 || raw_target > core::u32::MAX as i64 { - return Err(Error::new(ErrorKind::InvalidInput, "Invalid address")); + return Err(IoError::new(ErrorKind::InvalidInput, "Invalid address")); } let target_byte_addr = raw_target as u32; let address_same_block =