diff --git a/src/Tools/psxcdgen_ex/src/encoder/psx.rs b/src/Tools/psxcdgen_ex/src/encoder/psx.rs index 1b0c9b41..cff1d32f 100644 --- a/src/Tools/psxcdgen_ex/src/encoder/psx.rs +++ b/src/Tools/psxcdgen_ex/src/encoder/psx.rs @@ -1,7 +1,7 @@ use super::{*, Sector, SectorWriter, {CDDesc, Error}}; -use super::super::types::{layout::Layout, *}; +use super::super::types::{helper::PathTableMember, layout::Layout, *}; use builder::SubModeBuilder; -use cdtypes::types::{cdstring::{AString, DString}, date::*, dir_record::DirectoryRecord, helper::sector_count_mode2_form1, pvd as cd_pvd, lsb_msb::*, sector::Mode2Form1}; +use cdtypes::types::{cdstring::{AString, DString}, date::*, dir_record::DirectoryRecord, helper::sector_count_mode2_form1, path_table::*, pvd as cd_pvd, lsb_msb::*, sector::Mode2Form1}; const SYSTEM_AREA_SECTOR_COUNT:usize = 16; const PVD_SECTOR_COUNT:usize = 2; @@ -77,6 +77,7 @@ pub fn encode_psx_image(cd_desc: CDDesc, sec_writer: &mut dyn SectorWriter) -> R match element { Layout::SystemArea(system_area) => process_system_area(&system_area.borrow(), sec_writer)?, Layout::PVD(pvd) => process_pvd(&pvd.borrow(), cd_desc.path_table.clone(), cd_desc.root.clone(), vol_sector_count, sec_writer)?, + Layout::PathTables(path_table) => process_path_table(&path_table.borrow(), cd_desc.root.clone(), sec_writer)?, _ => () } } @@ -100,7 +101,7 @@ fn process_system_area(system_area: &SystemArea, sec_writer: &mut dyn SectorWrit fn process_pvd(pvd: &PrimaryVolumeDescriptor, path_table: SharedPtr, root_dir: SharedPtr, vol_sector_count: usize, sec_writer: &mut dyn SectorWriter) -> Result<(), Error> { const PLAYSATATION_STR:&'static str = "PLAYSTATION"; - let path_table = validate_path_table(&path_table)?; + let path_table = validate_and_unwrap_path_table(&path_table)?; let root_dir = root_dir.borrow(); let pvd_lba = pvd.track_rel_lba; @@ -142,17 +143,36 @@ fn process_pvd(pvd: &PrimaryVolumeDescriptor, path_table: SharedPtr, Ok(()) } -fn validate_path_table(path_table: &SharedPtr) -> Result, Error> { - let path_table = path_table.borrow(); +fn process_path_table(path_table: &PathTable, root_dir: SharedPtr, _sec_writer: &mut dyn SectorWriter) -> Result<(), Error> { + let mut bytes_used = 0; + let mut path_table_raw_l = vec![0u8; path_table.size_bytes]; + let mut path_table_raw_b = vec![0u8; path_table.size_bytes]; + let path_table = PathTable::collect_member(root_dir); + + for entry in path_table { + bytes_used += unsafe{update_path_table_entry(std::mem::transmute::<&mut u8, &mut PathTableL>(&mut path_table_raw_l[bytes_used]), std::mem::transmute::<&mut u8, &mut PathTableB>(&mut path_table_raw_b[bytes_used]), entry)?}; + } + + Err(Error::not_implemented("process_path_table")) +} + +fn validate_path_table(path_table: &PathTable) -> Result<(), Error> { if path_table.size_bytes > Mode2Form1::DATA_SIZE { Err(Error::from_text(format!("Path Tables are not allowed to be bigger then {} bytes - Path Table has {} bytes", Mode2Form1::DATA_SIZE, path_table.size_bytes))) } else { - Ok(path_table) + Ok(()) } } +fn validate_and_unwrap_path_table(path_table: &SharedPtr) -> Result, Error> { + let path_table = path_table.borrow(); + + validate_path_table(&path_table)?; + Ok(path_table) +} + fn update_dir_record(dir_record: &mut DirectoryRecord, dir: &Directory) -> Result<(), Error> { unsafe{dir_record.new(dir.name.as_str().unwrap_or("\x00"), false)}; @@ -162,4 +182,25 @@ fn update_dir_record(dir_record: &mut DirectoryRecord, dir: &Directory) -> Resul dir_record.set_directory(); Ok(()) +} + +fn update_path_table_entry(path_table_l: &mut PathTableL, path_table_b: &mut PathTableB, entry: PathTableMember) -> Result { + let name_len = entry.name.len(); + if name_len > 8 { + return Err(Error::from_text(format!("Directory name can not exceed size of 8 characters but folder {} has {} characters", entry.name, name_len))); + } + + unsafe{ + let name = entry.name.as_str(); + + path_table_l.new(name); + path_table_b.new(name); + } + + path_table_l.directory_logical_block.write(entry.track_rel_lba as u32); + path_table_b.directory_logical_block.write(entry.track_rel_lba as u32); + path_table_l.parent_table_id.write(entry.parent_table_id as u16); + path_table_b.parent_table_id.write(entry.parent_table_id as u16); + + Ok(path_table_l.get_size()) } \ No newline at end of file diff --git a/src/Tools/psxcdgen_ex/src/types/helper.rs b/src/Tools/psxcdgen_ex/src/types/helper.rs index 5295545e..55e544e0 100644 --- a/src/Tools/psxcdgen_ex/src/types/helper.rs +++ b/src/Tools/psxcdgen_ex/src/types/helper.rs @@ -1,10 +1,11 @@ use super::*; -const CURRENT_DIR_NAME:&'static str = "/x00"; -const PARENT_DIR_NAME:&'static str = "/x01"; +const CURRENT_DIR_NAME:&'static str = "\x00"; +const PARENT_DIR_NAME:&'static str = "\x01"; pub struct PathTableMember { pub name: String, + pub track_rel_lba: usize, pub parent_table_id: usize, } @@ -27,7 +28,10 @@ pub fn collect_path_table_member(root: SharedPtr) -> Vec) -> Vec) -> Vec { + helper::collect_path_table_member(root) + } + pub fn calculate_size_for(root: SharedPtr) -> usize { let mut size_bytes = 0; - helper::collect_path_table_member(root).into_iter().for_each(|element| { + Self::collect_member(root).into_iter().for_each(|element| { println!("PT: {} ^{}", element.name, element.parent_table_id); size_bytes += PathTableL::calculate_size_for(element.name.as_ref()); });