emu works again

This commit is contained in:
Alex Janka 2023-03-08 11:28:32 +11:00
parent 4bae07f165
commit aaca3ff5b2
8 changed files with 42 additions and 12 deletions

View file

@ -6,7 +6,7 @@ edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
gb-emu-lib = { path = "../lib" }
gb-emu-lib = { path = "../lib", features = [] }
clap = {version = "4.1.8", features = ["derive"]}
minifb = { path = "../vendored/rust_minifb" }
gilrs = "0.10.1"

View file

@ -85,7 +85,7 @@ fn main() {
cycle_count: args.cycle_count,
};
let tile_window: Option<Box<dyn Renderer>> = if args.tile_window {
let tile_window: Option<Box<dyn Renderer<u32>>> = if args.tile_window {
Some(Box::new(WindowRenderer::new(factor, None)))
} else {
None
@ -132,7 +132,7 @@ fn create_audio_output() -> (AudioOutput, Stream) {
let sample_rate = config.sample_rate().0;
let (output, mut rx) = AudioOutput::new(sample_rate as f32);
let (output, mut rx) = AudioOutput::new_unfilled(sample_rate as f32, true);
let stream = device
.build_output_stream(
@ -183,7 +183,7 @@ impl WindowRenderer {
}
}
impl Renderer for WindowRenderer {
impl Renderer<u32> for WindowRenderer {
fn prepare(&mut self, width: usize, height: usize) {
self.width = width;
self.height = height;

View file

@ -11,7 +11,7 @@ crate-type = ["cdylib", "rlib"]
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
gb-emu-lib = { path = "../lib" }
gb-emu-lib = { path = "../lib", features = ["async"] }
nih_plug = { path = "../vendored/nih-plug", features = ["standalone"] }
baseview = { path = "../vendored/baseview" }
pixels = "0.11.0"

View file

@ -107,7 +107,7 @@ impl Plugin for GameboyEmu {
};
let (sender, receiver) = channel::<EmulatorMessage>();
let (output, rx) = AudioOutput::new_unfilled(buffer_config.sample_rate);
let (output, rx) = AudioOutput::new_unfilled(buffer_config.sample_rate, false);
let (renderer, frame_receiver) = EmulatorRenderer::new();

View file

@ -5,6 +5,10 @@ edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[features]
default = []
async = []
[dependencies]
rand = "0.8.5"
async-ringbuf = "0.1.2"

View file

@ -13,6 +13,7 @@ pub enum RomFile {
Raw(Vec<u8>),
}
#[cfg(feature = "async")]
pub trait Renderer<Format: From<Colour>>: Send {
fn prepare(&mut self, width: usize, height: usize);
@ -25,26 +26,43 @@ pub trait Renderer<Format: From<Colour>>: Send {
fn set_rumble(&mut self, _rumbling: bool) {}
}
#[cfg(not(feature = "async"))]
pub trait Renderer<Format: From<Colour>> {
fn prepare(&mut self, width: usize, height: usize);
fn display(&mut self, buffer: &[Format]);
fn set_title(&mut self, _title: String) {}
fn latest_joypad_state(&mut self) -> JoypadState;
fn set_rumble(&mut self, _rumbling: bool) {}
}
pub struct AudioOutput {
pub sample_rate: f32,
pub send_rb: AsyncHeapProducer<[f32; 2]>,
pub wait_for_output: bool,
}
impl AudioOutput {
pub fn new(sample_rate: f32) -> (Self, AsyncHeapConsumer<[f32; 2]>) {
let (mut output, rx) = Self::new_unfilled(sample_rate);
pub fn new(sample_rate: f32, wait_for_output: bool) -> (Self, AsyncHeapConsumer<[f32; 2]>) {
let (mut output, rx) = Self::new_unfilled(sample_rate, wait_for_output);
executor::block_on(
output
.send_rb
.push_iter(vec![[0.; 2]; output.send_rb.len() - 1].into_iter()),
.push_iter(vec![[0.; 2]; output.send_rb.free_len() - 1].into_iter()),
)
.unwrap();
(output, rx)
}
pub fn new_unfilled(sample_rate: f32) -> (Self, AsyncHeapConsumer<[f32; 2]>) {
pub fn new_unfilled(
sample_rate: f32,
wait_for_output: bool,
) -> (Self, AsyncHeapConsumer<[f32; 2]>) {
let rb_len = sample_rate as usize / (60 * 2);
let rb = AsyncHeapRb::<[f32; 2]>::new(rb_len);
@ -54,6 +72,7 @@ impl AudioOutput {
Self {
sample_rate,
send_rb,
wait_for_output,
},
rx,
)

View file

@ -145,7 +145,10 @@ impl<ColourFormat: From<Colour> + Clone> Cpu<ColourFormat> {
self.set_or_clear_flag(Flags::Zero, result == 0x0);
self.set_or_clear_flag(
Flags::HalfCarry,
first.get_low_nibble() - (second.get_low_nibble() + if with_carry { 1 } else { 0 })
first
.get_low_nibble()
.borrowing_sub(second.get_low_nibble(), with_carry)
.0
> 0xF,
);
result

View file

@ -122,7 +122,11 @@ impl Apu {
}
fn push_audio(&mut self) {
let length = self.out_buffer.len().min(self.output.send_rb.free_len());
let length = if self.output.wait_for_output {
self.out_buffer.len()
} else {
self.out_buffer.len().min(self.output.send_rb.free_len())
};
executor::block_on(
self.output