Encode empty song sectors as CDXA Mode 1 for support with XEBRA

This commit is contained in:
Jaby 2024-06-19 20:28:04 +02:00
parent 087d139611
commit ab6caf77b3
5 changed files with 51 additions and 15 deletions

View File

@ -1,4 +1,4 @@
use crate::types::{helper::InterleavedXASizes, RawData};
use crate::types::{helper::{InterleavedXASector, InterleavedXASizes}, RawData};
use cdtypes::types::{helper::*, sector::*};
pub struct SubModeBuilder {
@ -100,7 +100,7 @@ pub fn create_xa_data_for_vec(sub_mode: Option<SubMode>, data: &RawData) -> Vec<
sectors
}
pub fn create_xa_audio_for(data: &Vec<RawData>) -> Vec<Mode2Form2> {
pub fn create_xa_audio_for(data: &Vec<RawData>) -> Vec<InterleavedXASector> {
let (channel_count, sectors_to_parse) = {
let size_info = InterleavedXASizes::new(data);
(size_info.channels, size_info.biggest_file_sectors)
@ -112,19 +112,19 @@ pub fn create_xa_audio_for(data: &Vec<RawData>) -> Vec<Mode2Form2> {
}
new_channel
};
let mut sectors = vec![Mode2Form2::new(); sectors_to_parse*channel_count];
let mut sectors = vec![InterleavedXASector::empty(); sectors_to_parse*channel_count];
let mut cur_sector_id = 0;
for _sector_id in 0..sectors_to_parse {
let mut channel_id = 0;
for channel in &mut channels {
let mut sub_mode = SubMode::default_form2();
let (raw_data, coding_info) = {
let sector = {
if channel.is_empty() {
sub_mode.set_eof();
sub_mode.set_eor();
([0xFFu8; Mode2Form2::DATA_SIZE], CodingInfo::default())
InterleavedXASector::data({
let mut sector = create_xa_data_zero();
sector.sub_header.channel_number = channel_id;
sector
})
}
else {
@ -140,12 +140,17 @@ pub fn create_xa_audio_for(data: &Vec<RawData>) -> Vec<Mode2Form2> {
// v Skip EDC
*channel = &channel[0x4..channel.len()];
sub_mode.set_real_time();
(raw_data, sub_header.coding_info)
let sub_mode = {
let mut sub_mode = SubMode::default_form2();
sub_mode.set_real_time();
sub_mode
};
InterleavedXASector::audio(create_xa_audio_for_raw(sub_mode, sub_header.coding_info, channel_id, &raw_data))
}
};
sectors[cur_sector_id] = create_xa_audio_for_raw(sub_mode, coding_info, channel_id, &raw_data);
sectors[cur_sector_id] = sector;
channel_id += 1;
cur_sector_id += 1;
}

View File

@ -346,7 +346,7 @@ fn process_file(file: &File, sec_writer: &mut dyn SectorWriter) -> Result<(), Er
let content_sector_count = content_sectors.len();
for sector in content_sectors {
sec_writer.write_cd_xa_audio(sector)?;
sec_writer.write_interleaved(sector)?;
}
let extended_sector_count = sector_count_mode2_form2(padded_size) - content_sector_count;

View File

@ -1,7 +1,9 @@
pub mod bin_cue;
pub use cdtypes::{cd::sector::Sector, types::*};
use sector::Mode0;
use crate::types::helper::InterleavedXASector;
use super::{encoder::ImageEncoderFunction, types::CDDesc};
use bin_cue::BinCueWriter;
use clap::ValueEnum;
@ -34,6 +36,14 @@ pub trait SectorWriter {
self.write(Sector::CDXAAudio(sector))
}
fn write_interleaved(&mut self, sector: InterleavedXASector) -> Result<usize, Error> {
match sector {
InterleavedXASector::Empty => self.write_empty(Mode0::new()),
InterleavedXASector::Data(sector) => self.write_cd_xa_data(sector),
InterleavedXASector::Audio(sector) => self.write_cd_xa_audio(sector),
}
}
fn write(&mut self, sector: Sector) -> Result<usize, Error>;
fn cd_da_start(&mut self) -> Result<(), Error>;
}

View File

@ -1,10 +1,31 @@
use cdtypes::types::helper::sector_count_audio;
use cdtypes::types::{helper::sector_count_audio, sector::{Mode2Form1, Mode2Form2}};
use super::*;
const CURRENT_DIR_NAME:&'static str = "\x00";
const PARENT_DIR_NAME:&'static str = "\x01";
#[derive(Clone)]
pub enum InterleavedXASector {
Empty,
Data(Mode2Form1),
Audio(Mode2Form2)
}
impl InterleavedXASector {
pub fn empty() -> InterleavedXASector {
InterleavedXASector::Empty
}
pub fn data(sector: Mode2Form1) -> InterleavedXASector {
InterleavedXASector::Data(sector)
}
pub fn audio(sector: Mode2Form2) -> InterleavedXASector {
InterleavedXASector::Audio(sector)
}
}
pub struct PathTableMember {
pub name: String,
pub track_rel_lba: usize,

View File

@ -3,7 +3,7 @@ pub mod layout;
pub mod file_map;
pub mod overlay;
use cdtypes::types::{cdstring::DString, dir_record::DirectoryRecord, helper::xa_audio_interleave_count, path_table::PathTableL, sector::{AudioSample, Mode2Form2}};
use cdtypes::types::{cdstring::DString, dir_record::DirectoryRecord, helper::xa_audio_interleave_count, path_table::PathTableL, sector::AudioSample};
use std::{cell::RefCell, path::PathBuf, rc::Rc};
pub use file_map::FileSystemMap;