From 3ccd2006af80471967f4be1c701ba6013dd28b4f Mon Sep 17 00:00:00 2001 From: Atreya Bain Date: Sun, 18 Feb 2024 09:46:10 +0530 Subject: [PATCH] [pcr] Implement PC --- src/emu/iomem.rs | 15 +++++++-------- src/emu/mod.rs | 3 ++- src/emu/program_counter.rs | 38 ++++++++++++++++++++++++++++++++++++++ 3 files changed, 47 insertions(+), 9 deletions(-) create mode 100644 src/emu/program_counter.rs diff --git a/src/emu/iomem.rs b/src/emu/iomem.rs index 04a12e5..ca3e720 100644 --- a/src/emu/iomem.rs +++ b/src/emu/iomem.rs @@ -1,4 +1,5 @@ use crate::emu::mmu::Memory; +use crate::emu::program_counter::ProgramCounter; use crate::misc::emulator_error::EmulatorError; use crate::misc::endian::{read_big_endian_u16, read_big_endian_u24}; use crate::misc::result::EmulatorResult; @@ -7,13 +8,13 @@ use crate::misc::result::EmulatorResult; pub struct MemoryMappedIO { //FIXME use a keyboard keyboard_bytes: [u8; 2], - program_counter: [u8; 3], + program_counter: ProgramCounter, //FIXME use a device pixel_reg: u8, //FIXME use a device audio_sample_address_base: [u8; 2], } - +/// Represents the memory mapped segment of IO. Aggregates the mapping logic. impl MemoryMappedIO { // 2 byte keyboard bits pub const KEYBOARD_BIT_START: u32 = 0; @@ -32,10 +33,10 @@ impl MemoryMappedIO { pub const AUDIO_SAMPLE_BASE_LEN: u32 = 2; const AUDIO_SAMPLE_BASE_END: u32 = Self::AUDIO_SAMPLE_BASE_START + Self::AUDIO_SAMPLE_BASE_LEN - 1; - pub fn new() -> MemoryMappedIO { + pub fn new(program_counter: ProgramCounter) -> MemoryMappedIO { MemoryMappedIO { keyboard_bytes: [0, 0], - program_counter: [0, 0, 0], + program_counter, pixel_reg: 0, audio_sample_address_base: [0, 0], } @@ -53,10 +54,8 @@ impl Memory for MemoryMappedIO { keyboard_byte } Self::PC_START_ADDR..=Self::PC_END_ADDR => { - let pc_index = (address - Self::PC_START_ADDR) as usize; - let pc_byte = self.program_counter[pc_index]; - log::trace!("Fetching PC({}) byte segment {} -> {}",read_big_endian_u24(&self.program_counter),pc_index,pc_byte); - pc_byte + let pc_index = address - Self::PC_START_ADDR; + self.program_counter.try_get_byte(pc_index)? } Self::PIXEL_BASE => { log::trace!("Fetching pixel base reg {}",self.pixel_reg); diff --git a/src/emu/mod.rs b/src/emu/mod.rs index a2169e4..6c70821 100644 --- a/src/emu/mod.rs +++ b/src/emu/mod.rs @@ -1,4 +1,5 @@ pub mod cpu; pub mod mmu; pub mod ram; -pub mod iomem; \ No newline at end of file +pub mod iomem; +mod program_counter; \ No newline at end of file diff --git a/src/emu/program_counter.rs b/src/emu/program_counter.rs new file mode 100644 index 0000000..4af8327 --- /dev/null +++ b/src/emu/program_counter.rs @@ -0,0 +1,38 @@ +use crate::emu::mmu::Memory; +use crate::misc::emulator_error::DeviceType::PC; +use crate::misc::emulator_error::EmulatorError; +use crate::misc::endian::{read_big_endian_u24, write_big_endian_u24}; +use crate::misc::result::EmulatorResult; + + +#[derive(Debug,Default, Copy, Clone)] +pub struct ProgramCounter { + /// 24bit location register + program_counter_register: [u8; 3], +} + +impl ProgramCounter { + // get the current program counter as an address + pub fn get_pc_value(&self) -> u32 { + read_big_endian_u24(&self.program_counter_register) + } + // assign a value of PC to start execution + pub fn set_address(&mut self, address: u32) { + log::debug!("Setting PC as {}",address); + write_big_endian_u24(address, &mut self.program_counter_register) + } +} +/// Allow Using Program counter as mapped memory +impl Memory for ProgramCounter { + fn try_get_byte(&self, address: u32) -> EmulatorResult { + log::trace!("Fetching PC({}) byte segment index {}",read_big_endian_u24(&self.program_counter_register),address); + self.program_counter_register.get(address as usize) + .map(|e| *e) + .ok_or(EmulatorError::UnreachableMemory(PC, address)) + } + /// TODO: Set a byte of PC from the memory. + fn try_set_byte(&mut self, address: u32, value: u8) -> EmulatorResult<()> { + log::error!("Unsupported Method!"); + todo!() + } +} \ No newline at end of file