dont asplode stack

This commit is contained in:
Alex Janka 2023-10-26 15:45:01 +11:00
parent 5d61d4466a
commit e0e7634aec
2 changed files with 38 additions and 17 deletions

View file

@ -321,12 +321,16 @@ where
0x0..0xFF40 | 0xFF4C..=0xFFFF => unreachable!(),
},
IoAddress::Cgb(address) => {
if let WramBanks::Cgb { banks: _, selected } = &self.ram.banks && let Some(cgb_peripherals) = &self.cgb_peripherals {
if let WramBanks::Cgb { banks: _, selected } = &self.ram.banks
&& let Some(cgb_peripherals) = &self.cgb_peripherals
{
match address {
CgbIoAddress::CompatMode => self.gpu.get_compat_byte(),
CgbIoAddress::PrepareSpeed => cgb_peripherals.double_speed.get(),
CgbIoAddress::VramBank => self.gpu.vram.get_vram_bank(),
CgbIoAddress::VramDma(address) => cgb_peripherals.vram_dma.get_register(address),
CgbIoAddress::VramDma(address) => {
cgb_peripherals.vram_dma.get_register(address)
}
CgbIoAddress::Infrared => cgb_peripherals.infrared.get(),
CgbIoAddress::Palette(address) => self.gpu.get_cgb_palette(address),
CgbIoAddress::ObjPriority => self.gpu.get_obj_priority(),
@ -380,18 +384,22 @@ where
0x0..0xFF40 | 0xFF4C..=0xFFFF => unreachable!(),
},
IoAddress::Cgb(address) => {
if let WramBanks::Cgb { banks: _, selected } = &mut self.ram.banks && let Some(cgb_peripherals) = &mut self.cgb_peripherals {
if let WramBanks::Cgb { banks: _, selected } = &mut self.ram.banks
&& let Some(cgb_peripherals) = &mut self.cgb_peripherals
{
match address {
CgbIoAddress::CompatMode => self.gpu.set_compat_byte(data),
CgbIoAddress::PrepareSpeed => cgb_peripherals.double_speed.set(data),
CgbIoAddress::VramBank => self.gpu.vram.set_vram_bank(data),
CgbIoAddress::VramDma(address) => cgb_peripherals.vram_dma.set_register(address, data),
CgbIoAddress::VramDma(address) => {
cgb_peripherals.vram_dma.set_register(address, data)
}
CgbIoAddress::Infrared => cgb_peripherals.infrared.set(data),
CgbIoAddress::Palette(address) => self.gpu.set_cgb_palette(address, data),
CgbIoAddress::ObjPriority => self.gpu.set_obj_priority(data),
CgbIoAddress::WramBank => *selected = (data & 0b111).max(1) as usize,
CgbIoAddress::Pcm12 => {},
CgbIoAddress::Pcm34 => {},
CgbIoAddress::Pcm12 => {}
CgbIoAddress::Pcm34 => {}
CgbIoAddress::Unused(v) => {
eprintln!("attempt to set 0x{v:0>4X} to 0x{data:0>2X}")
}

View file

@ -25,11 +25,13 @@ mod types;
const TILE_WINDOW_WIDTH: usize = 16 * 8;
const TILE_WINDOW_HEIGHT: usize = 24 * 8;
type Buffer<ColourFormat, const SIZE: usize> = Box<[ColourFormat; SIZE]>;
pub struct Gpu<ColourFormat>
where
ColourFormat: From<Colour> + Copy,
{
pub buffer: [ColourFormat; WIDTH * HEIGHT],
pub buffer: Buffer<ColourFormat, { WIDTH * HEIGHT }>,
pub vram: Vram,
pub oam: Oam,
pub window: Sender<RendererMessage<ColourFormat>>,
@ -43,7 +45,7 @@ where
tile_window: Option<TileWindow<ColourFormat>>,
layer_window: Option<(
Sender<RendererMessage<ColourFormat>>,
[ColourFormat; WIDTH * HEIGHT * 3],
Buffer<ColourFormat, { WIDTH * HEIGHT * 3 }>,
)>,
window_lc: u8,
has_window_been_enabled: bool,
@ -71,7 +73,12 @@ where
let tile_window = tile_window_renderer
.map(|tile_window_renderer| TileWindow::new(tile_window_renderer, cgb));
let buffer = [get_blank_colour(cgb); WIDTH * HEIGHT];
let buffer = {
let mut v: Vec<ColourFormat> = Vec::new();
v.resize(WIDTH * HEIGHT, get_blank_colour(cgb));
let temp = v.into_boxed_slice();
unsafe { Box::from_raw(Box::into_raw(temp) as *mut [ColourFormat; WIDTH * HEIGHT]) }
};
let layer_window = layer_window_renderer.map(|layer_window_renderer| {
layer_window_renderer
@ -80,10 +87,14 @@ where
height: HEIGHT * 3,
})
.expect("message error");
(
layer_window_renderer,
[get_blank_colour(cgb); WIDTH * HEIGHT * 3],
)
(layer_window_renderer, {
let mut v: Vec<ColourFormat> = Vec::new();
v.resize(WIDTH * HEIGHT * 3, get_blank_colour(cgb));
let temp = v.into_boxed_slice();
unsafe {
Box::from_raw(Box::into_raw(temp) as *mut [ColourFormat; WIDTH * HEIGHT * 3])
}
})
});
Self {
@ -224,7 +235,9 @@ where
self.window_lc = 0;
self.has_window_been_enabled = false;
let is_cgb_mode = self.is_cgb_mode();
if let Some(tile_window) = &mut self.tile_window && output {
if let Some(tile_window) = &mut self.tile_window
&& output
{
tile_window.draw_sprite_window(self.bg_palette, &self.vram, is_cgb_mode);
}
}
@ -493,19 +506,19 @@ where
fn render_window(&mut self) {
let mut buffer = Vec::new();
buffer.extend_from_slice(&self.buffer);
buffer.extend_from_slice(self.buffer.as_ref());
self.window
.send(RendererMessage::display_message(buffer))
.expect("message error");
if let Some((ref mut window, ref mut buffer)) = self.layer_window {
let mut new_buffer = Vec::new();
new_buffer.extend_from_slice(buffer);
new_buffer.extend_from_slice(buffer.as_ref());
window
.send(RendererMessage::display_message(new_buffer))
.expect("message error");
for val in buffer {
for val in buffer.iter_mut() {
*val = get_blank_colour(self.cgb_data.is_some());
}
}