Skip to content

Commit

Permalink
Read vram in render thread
Browse files Browse the repository at this point in the history
  • Loading branch information
Grarak committed Jan 19, 2025
1 parent e8bc9da commit 64bf130
Show file tree
Hide file tree
Showing 5 changed files with 200 additions and 155 deletions.
13 changes: 6 additions & 7 deletions src/core/graphics/gpu.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ use crate::core::CpuType::ARM9;
use crate::logging::debug_println;
use bilge::prelude::*;
use std::intrinsics::unlikely;
use std::ptr;
use std::ptr::NonNull;
use std::sync::atomic::{AtomicU16, Ordering};
use std::sync::Arc;
Expand Down Expand Up @@ -171,15 +170,15 @@ impl Gpu {
gpu.v_count += 1;
match gpu.v_count {
192 => {
let pow_cnt1 = PowCnt1::from(gpu.pow_cnt1);
let gpu_3d_regs_ptr = ptr::addr_of_mut!(gpu.gpu_3d_regs);
gpu.get_renderer_mut().on_scanline_finish(get_mem_mut!(emu), pow_cnt1, unsafe { gpu_3d_regs_ptr.as_mut_unchecked() });

if gpu.gpu_3d_regs.flushed {
gpu.gpu_3d_regs.swap_buffers();
let gpu_3d_regs = &mut get_common_mut!(emu).gpu.gpu_3d_regs;
if gpu_3d_regs.flushed {
gpu_3d_regs.swap_buffers();
gpu.get_renderer_mut().renderer_3d.invalidate();
}

let pow_cnt1 = PowCnt1::from(gpu.pow_cnt1);
gpu.get_renderer_mut().on_scanline_finish(get_mem_mut!(emu), pow_cnt1, gpu_3d_regs);

for i in 0..2 {
let disp_stat = &mut gpu.disp_stat[i];
disp_stat.set_v_blank_flag(u1::new(1));
Expand Down
68 changes: 47 additions & 21 deletions src/core/graphics/gpu_mem_buf.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,16 @@
use crate::core::memory::mem::Memory;
use crate::core::memory::vram::VramMaps;
use crate::core::memory::{regions, vram};
use crate::utils::HeapMemU8;
use std::ptr::NonNull;
use std::slice;

#[derive(Default)]
pub struct GpuMemBuf {
vram_maps: VramMaps,
pub palettes_ptr: Option<NonNull<u8>>,
pub oam_ptr: Option<NonNull<u8>>,

pub lcdc: HeapMemU8<{ vram::TOTAL_SIZE }>,

pub bg_a: HeapMemU8<{ vram::BG_A_SIZE as usize }>,
Expand All @@ -26,36 +33,55 @@ pub struct GpuMemBuf {
}

impl GpuMemBuf {
pub fn read_2d(&mut self, mem: &mut Memory, read_lcdc: bool) {
pub fn set_vram_maps(&mut self, vram_maps: VramMaps) {
self.vram_maps = vram_maps;
}

pub fn set_palettes_oam(&mut self, mem: &mut Memory) {
if mem.palettes.dirty {
self.palettes_ptr = NonNull::new(mem.palettes.mem.as_mut_ptr());
mem.palettes.dirty = false;
} else {
self.palettes_ptr = None;
}
if mem.oam.dirty {
self.oam_ptr = NonNull::new(mem.oam.mem.as_mut_ptr());
mem.oam.dirty = false;
} else {
self.oam_ptr = None;
}
}

pub fn read_2d(&mut self, read_lcdc: bool) {
if read_lcdc {
mem.vram.read_all_lcdc(&mut self.lcdc);
self.vram_maps.read_all_lcdc(&mut self.lcdc);
}

mem.vram.read_all_bg_a(&mut self.bg_a);
mem.vram.read_all_obj_a(&mut self.obj_a);
mem.vram.read_all_bg_a_ext_palette(&mut self.bg_a_ext_palette);
mem.vram.read_all_obj_a_ext_palette(&mut self.obj_a_ext_palette);
self.vram_maps.read_all_bg_a(&mut self.bg_a);
self.vram_maps.read_all_obj_a(&mut self.obj_a);
self.vram_maps.read_all_bg_a_ext_palette(&mut self.bg_a_ext_palette);
self.vram_maps.read_all_obj_a_ext_palette(&mut self.obj_a_ext_palette);

mem.vram.read_bg_b(&mut self.bg_b);
mem.vram.read_all_obj_b(&mut self.obj_b);
mem.vram.read_all_bg_b_ext_palette(&mut self.bg_b_ext_palette);
mem.vram.read_all_obj_b_ext_palette(&mut self.obj_b_ext_palette);
self.vram_maps.read_bg_b(&mut self.bg_b);
self.vram_maps.read_all_obj_b(&mut self.obj_b);
self.vram_maps.read_all_bg_b_ext_palette(&mut self.bg_b_ext_palette);
self.vram_maps.read_all_obj_b_ext_palette(&mut self.obj_b_ext_palette);

if mem.palettes.dirty {
mem.palettes.dirty = false;
self.pal_a.copy_from_slice(&mem.palettes.mem[..mem.palettes.mem.len() / 2]);
self.pal_b.copy_from_slice(&mem.palettes.mem[mem.palettes.mem.len() / 2..]);
if let Some(ptr) = self.palettes_ptr {
let slice = unsafe { slice::from_raw_parts(ptr.as_ptr(), regions::STANDARD_PALETTES_SIZE as usize) };
self.pal_a.copy_from_slice(&slice[..regions::STANDARD_PALETTES_SIZE as usize / 2]);
self.pal_b.copy_from_slice(&slice[regions::STANDARD_PALETTES_SIZE as usize / 2..]);
}

if mem.oam.dirty {
mem.oam.dirty = false;
self.oam_a.copy_from_slice(&mem.oam.mem[..mem.oam.mem.len() / 2]);
self.oam_b.copy_from_slice(&mem.oam.mem[mem.oam.mem.len() / 2..]);
if let Some(ptr) = self.oam_ptr {
let slice = unsafe { slice::from_raw_parts(ptr.as_ptr(), regions::OAM_SIZE as usize) };
self.oam_a.copy_from_slice(&slice[..regions::OAM_SIZE as usize / 2]);
self.oam_b.copy_from_slice(&slice[regions::OAM_SIZE as usize / 2..]);
}
}

pub fn read_3d(&mut self, mem: &mut Memory) {
mem.vram.read_all_tex_rear_plane_img(&mut self.tex_rear_plane_image);
mem.vram.read_all_tex_palette(&mut self.tex_pal);
pub fn read_3d(&mut self) {
self.vram_maps.read_all_tex_rear_plane_img(&mut self.tex_rear_plane_image);
self.vram_maps.read_all_tex_palette(&mut self.tex_pal);
}
}
8 changes: 6 additions & 2 deletions src/core/graphics/gpu_renderer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -74,12 +74,13 @@ impl GpuRenderer {
self.common.pow_cnt1 = pow_cnt1;
self.renderer_2d.on_scanline_finish();

self.common.mem_buf.read_2d(mem, self.renderer_2d.has_vram_display[0]);
self.common.mem_buf.set_vram_maps(mem.vram.maps.clone());
self.common.mem_buf.set_palettes_oam(mem);
mem.vram.maps.undirty(self.renderer_2d.has_vram_display[0]);
if self.renderer_3d.dirty {
self.renderer_3d.finish_scanline(registers_3d);
self.renderer_3d.dirty = false;
self.rendering_3d = true;
self.common.mem_buf.read_3d(mem);
}

*rendering = true;
Expand Down Expand Up @@ -123,6 +124,9 @@ impl GpuRenderer {
);
};

self.common.mem_buf.read_2d(self.renderer_2d.has_vram_display[0]);
self.common.mem_buf.read_3d();

if self.rendering_3d {
self.rendering_3d = false;
self.renderer_3d.render(&self.common);
Expand Down
Loading

0 comments on commit 64bf130

Please sign in to comment.