Updated readme
This commit is contained in:
parent
5c7c9d065f
commit
8b8430bf13
47
README.md
47
README.md
|
@ -15,8 +15,8 @@ For more detail, check out this post about how I started the project:
|
|||
[Making a 68000 Emulator in Rust](https://jabberwocky.ca/posts/2021-11-making_an_emulator.html)
|
||||
|
||||
|
||||
Running
|
||||
-------
|
||||
Computie
|
||||
--------
|
||||
|
||||
For Computie, it can do everything the 68k-SMT board can do, including run the
|
||||
monitor program and load the Computie OS kernel and boot it from the
|
||||
|
@ -32,6 +32,9 @@ host, and set up host routing. The exact commands in
|
|||
`src/machines/computie.rs` might need to be adjusted to work on different
|
||||
hosts.
|
||||
|
||||
TRS-80
|
||||
------
|
||||
|
||||
For the TRS-80, it can run Level I or Level II Basic, but it doesn't yet
|
||||
support a cassette tape drive or floppy drive. I haven't tested it that
|
||||
thoroughly either, so any help with it would be welcome. I mostly made it to
|
||||
|
@ -40,16 +43,50 @@ Genesis emulator. The frontend uses the
|
|||
[`minifb`](https://github.com/emoon/rust_minifb) rust crate to open a window
|
||||
and render the characters to screen, as well as accept input from the keyboard.
|
||||
```
|
||||
cargo run -p moa-minifb --release --bin moa-trs-80 --
|
||||
cargo run -p moa-minifb --release --bin moa-trs-80
|
||||
```
|
||||
By default it will start Level I Basic. To use the other rom, add the option
|
||||
`--rom binaries/trs80/level2.rom`
|
||||
|
||||
The Genesis emulator is a work in progress but can be run with:
|
||||
![alt text](images/trs-80-level-ii-basic.png)
|
||||
|
||||
Sega Genesis/MegaDrive
|
||||
----------------------
|
||||
|
||||
It can be run with:
|
||||
```
|
||||
cargo run -p moa-minifb --release --bin moa-genesis
|
||||
cargo run -p moa-minifb --release --bin moa-genesis -- <ROM FILE>
|
||||
```
|
||||
|
||||
The Genesis emulator is a work in progress. It can play a few games but some
|
||||
games won't run because the bank switching for the Z80 coprocessor is not
|
||||
working yet, and some games will hang waiting for the Z80 to respond. For the
|
||||
video processor, the window layer is not drawn and the layer priority is not
|
||||
handled. The horizontal scroll also doesn't work on a line-by-line basis so it
|
||||
tends to be quite jerky as you move, with the sprites and cells misaligned
|
||||
until you've moved one complete cell over (8x8 pixels).
|
||||
|
||||
On the Sonic 2 title screen, the colours for Tails are wonky, probably because
|
||||
there's some trickery going on to get more than 16 colours per line, but the
|
||||
emulator currently renders the whole frame at once instead of line by line, so
|
||||
changes that should be made while the screen is updating don't show up
|
||||
![alt text](images/sega-genesis-sonic2-title.png)
|
||||
|
||||
In the first one, it's mostly working but the bottom of the clouds should be a
|
||||
different colour. Highlight/Shadow colours are not yet supported
|
||||
![alt text](sega-genesis-sonic2-start.png)
|
||||
|
||||
I'm not yet sure why the clouds in the background are cut off suddenly
|
||||
![alt text](sega-genesis-sonic2-bridge.png)
|
||||
|
||||
There are some graphics glitches in Earthworm Jim, but it's almost playable if it
|
||||
wasn't for the 'jump' button, which only makes him jump a few pixels
|
||||
![alt text](sega-genesis-earthworm-jim.png)
|
||||
|
||||
|
||||
General Options
|
||||
---------------
|
||||
|
||||
By default, the minifb frontend will scale the window by 2. This can be
|
||||
changed with the `--scale [1,2,4]` option.
|
||||
|
||||
|
|
|
@ -1,14 +1,20 @@
|
|||
|
||||
|
||||
use moa_minifb;
|
||||
use moa::machines::genesis::build_genesis;
|
||||
use moa::machines::genesis::{build_genesis, SegaGenesisOptions};
|
||||
|
||||
fn main() {
|
||||
let matches = moa_minifb::new("Sega Genesis/Mega Drive Emulator")
|
||||
.arg("<ROM> 'ROM file to load (must be flat binary)'")
|
||||
.get_matches();
|
||||
|
||||
let mut options = SegaGenesisOptions::new();
|
||||
if let Some(filename) = matches.value_of("ROM") {
|
||||
options.rom = filename.to_string();
|
||||
}
|
||||
|
||||
moa_minifb::run(matches, |frontend| {
|
||||
build_genesis(frontend)
|
||||
build_genesis(frontend, options)
|
||||
});
|
||||
}
|
||||
|
||||
|
|
Binary file not shown.
After Width: | Height: | Size: 34 KiB |
Binary file not shown.
After Width: | Height: | Size: 26 KiB |
Binary file not shown.
After Width: | Height: | Size: 25 KiB |
Binary file not shown.
After Width: | Height: | Size: 26 KiB |
Binary file not shown.
After Width: | Height: | Size: 6.8 KiB |
|
@ -14,15 +14,29 @@ use crate::peripherals::genesis;
|
|||
use crate::host::traits::{Host};
|
||||
|
||||
|
||||
pub fn build_genesis<H: Host>(host: &mut H) -> Result<System, Error> {
|
||||
pub struct SegaGenesisOptions {
|
||||
pub rom: String,
|
||||
}
|
||||
|
||||
impl SegaGenesisOptions {
|
||||
pub fn new() -> Self {
|
||||
Self {
|
||||
rom: "".to_string(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub fn build_genesis<H: Host>(host: &mut H, options: SegaGenesisOptions) -> Result<System, Error> {
|
||||
let mut system = System::new();
|
||||
|
||||
let mut rom = MemoryBlock::load(&options.rom).unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/GenTestV3.0.bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/HDRV_Genesis_Test_v1_4.bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/ComradeOj's tiny demo.bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/Digital Rain demo.bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/Sonic The Hedgehog (W) (REV 00) [!].bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/Sonic The Hedgehog (W) (REV 01) [!].bin").unwrap();
|
||||
let mut rom = MemoryBlock::load("binaries/genesis/Sonic the Hedgehog 2 (JUE) [!].bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/Sonic the Hedgehog 2 (JUE) [!].bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/Sonic the Hedgehog 3 (U) [!].bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/Earthworm Jim (U) [h1].bin").unwrap();
|
||||
//let mut rom = MemoryBlock::load("binaries/genesis/Home Alone (beta).bin").unwrap();
|
||||
|
@ -50,7 +64,7 @@ pub fn build_genesis<H: Host>(host: &mut H) -> Result<System, Error> {
|
|||
let bus_request = coproc.bus_request.clone();
|
||||
|
||||
system.add_addressable_device(0x00a00000, coproc_mem)?;
|
||||
//system.add_device("coproc", wrap_transmutable(coproc))?;
|
||||
system.add_device("coproc", wrap_transmutable(coproc))?;
|
||||
|
||||
|
||||
|
||||
|
@ -65,27 +79,7 @@ pub fn build_genesis<H: Host>(host: &mut H) -> Result<System, Error> {
|
|||
system.add_peripheral("vdp", 0x00c00000, wrap_transmutable(vdp)).unwrap();
|
||||
|
||||
|
||||
// TODO this is temporarily a 68010 because GenTest tests the CPU type by relying on the illegal instruction
|
||||
// exception which is bypassed to Error and I don't want to un-bypass yet while testing
|
||||
let mut cpu = M68k::new(M68kType::MC68010, 7_670_454, BusPort::new(0, 24, 16, system.bus.clone()));
|
||||
|
||||
//cpu.enable_tracing();
|
||||
//cpu.add_breakpoint(0x206);
|
||||
//cpu.add_breakpoint(0x1dd0); // Sonic: some kind of palette fading function
|
||||
//cpu.add_breakpoint(0x16ee);
|
||||
//cpu.decoder.dump_disassembly(&mut system, 0x206, 0x2000);
|
||||
|
||||
//cpu.add_breakpoint(0x16a0e);
|
||||
//cpu.add_breakpoint(0x16812);
|
||||
//cpu.add_breakpoint(0x166ec);
|
||||
//cpu.add_breakpoint(0x13e18);
|
||||
//cpu.add_breakpoint(0x16570);
|
||||
//cpu.add_breakpoint(0x1714);
|
||||
|
||||
//cpu.add_breakpoint(0x43c2);
|
||||
|
||||
//cpu.add_breakpoint(0x21a);
|
||||
|
||||
let mut cpu = M68k::new(M68kType::MC68000, 7_670_454, BusPort::new(0, 24, 16, system.bus.clone()));
|
||||
system.add_interruptable_device("cpu", wrap_transmutable(cpu)).unwrap();
|
||||
|
||||
Ok(system)
|
||||
|
|
|
@ -418,9 +418,8 @@ impl Ym7101State {
|
|||
|
||||
for cell_y in 0..cells_v {
|
||||
for cell_x in 0..cells_h {
|
||||
let pattern_addr = self.get_pattern_addr(cell_table, cell_x as usize, cell_y as usize);
|
||||
let pattern = read_beu16(&self.vram[pattern_addr..]);
|
||||
self.draw_pattern(frame, pattern, (cell_x << 3) as u32, (cell_y << 3) as u32);
|
||||
let pattern_w = read_beu16(&self.vram[self.get_pattern_addr(cell_table, cell_x as usize, cell_y as usize)..]);
|
||||
self.draw_pattern(frame, pattern_w, (cell_x << 3) as u32, (cell_y << 3) as u32);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue