Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
boytacean
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Wiki
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Snippets
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Package registry
Container Registry
Model registry
Operate
Environments
Terraform modules
Monitor
Incidents
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
João Magalhães
boytacean
Commits
9386638f
Verified
Commit
9386638f
authored
1 year ago
by
João Magalhães
Browse files
Options
Downloads
Patches
Plain Diff
chore: initial support for multiple vram banks
parent
20cd3a25
No related branches found
No related tags found
1 merge request
!16
Support for Game Boy Color (CGB) 😎🖍️
Pipeline
#2604
failed
1 year ago
Stage: build
Stage: test
Changes
2
Pipelines
1
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
src/mmu.rs
+4
-1
4 additions, 1 deletion
src/mmu.rs
src/ppu.rs
+49
-8
49 additions, 8 deletions
src/ppu.rs
with
53 additions
and
9 deletions
src/mmu.rs
+
4
−
1
View file @
9386638f
...
...
@@ -69,6 +69,9 @@ pub struct Mmu {
/// the 0xD000-0xDFFF memory range (CGB only).
ram_bank
:
u8
,
/// The offset to be used in the read and write operation of
/// the RAM, this value should be consistent with the RAM bank
/// that is currently selected (CGB only).
ram_offset
:
u16
,
mode
:
GameBoyMode
,
...
...
@@ -323,7 +326,7 @@ impl Mmu {
// 0xFF70 - SVBK: WRAM bank (CGB only)
0x70
=>
{
let
mut
ram_bank
=
value
&
0x7
;
let
mut
ram_bank
=
value
&
0x
0
7
;
if
ram_bank
==
0x0
{
ram_bank
=
0x1
;
}
...
...
This diff is collapsed.
Click to expand it.
src/ppu.rs
+
49
−
8
View file @
9386638f
...
...
@@ -9,7 +9,9 @@ use wasm_bindgen::prelude::*;
use
crate
::
warnln
;
pub
const
VRAM_SIZE
:
usize
=
8192
;
pub
const
VRAM_SIZE_DMG
:
usize
=
8192
;
pub
const
VRAM_SIZE_CGB
:
usize
=
16384
;
pub
const
VRAM_SIZE
:
usize
=
VRAM_SIZE_CGB
;
pub
const
HRAM_SIZE
:
usize
=
128
;
pub
const
OAM_SIZE
:
usize
=
260
;
pub
const
PALETTE_SIZE
:
usize
=
4
;
...
...
@@ -19,9 +21,12 @@ pub const TILE_WIDTH: usize = 8;
pub
const
TILE_HEIGHT
:
usize
=
8
;
pub
const
TILE_DOUBLE_HEIGHT
:
usize
=
16
;
pub
const
TILE_COUNT_DMG
:
usize
=
384
;
pub
const
TILE_COUNT_CGB
:
usize
=
768
;
/// The number of tiles that can be store in Game Boy's
/// VRAM memory according to specifications.
pub
const
TILE_COUNT
:
usize
=
384
;
pub
const
TILE_COUNT
:
usize
=
TILE_COUNT_CGB
;
/// The number of objects/sprites that can be handled at
/// the same time by the Game Boy.
...
...
@@ -161,6 +166,26 @@ impl Display for ObjectData {
}
}
#[cfg_attr(feature
=
"wasm"
,
wasm_bindgen)]
#[derive(Clone,
Copy,
PartialEq,
Eq)]
pub
struct
TileData
{
palette
:
u8
,
vram_bank
:
u8
,
xflip
:
bool
,
yflip
:
bool
,
priority
:
bool
,
}
impl
Display
for
TileData
{
fn
fmt
(
&
self
,
f
:
&
mut
Formatter
<
'_
>
)
->
fmt
::
Result
{
write!
(
f
,
"Palette => {}
\n
VRAM Bank => {}
\n
X Flip => {}
\n
Y Flip => {}"
,
self
.palette
,
self
.vram_bank
,
self
.xflip
,
self
.yflip
)
}
}
pub
struct
PpuRegisters
{
pub
scy
:
u8
,
pub
scx
:
u8
,
...
...
@@ -203,6 +228,15 @@ pub struct Ppu {
/// sprite attributes for each of the 40 sprites of the Game Boy.
oam
:
[
u8
;
OAM_SIZE
],
/// The VRAM bank to be used in the read and write operation of
/// the 0x8000-0x9FFF memory range (CGB only).
vram_bank
:
u8
,
/// The offset to be used in the read and write operation of
/// the VRAM, this value should be consistent with the VRAM bank
/// that is currently selected (CGB only).
vram_offset
:
u16
,
/// The current set of processed tiles that are store in the
/// PPU related structures.
tiles
:
[
Tile
;
TILE_COUNT
],
...
...
@@ -366,6 +400,8 @@ impl Ppu {
vram
:
[
0u8
;
VRAM_SIZE
],
hram
:
[
0u8
;
HRAM_SIZE
],
oam
:
[
0u8
;
OAM_SIZE
],
vram_bank
:
0x0
,
vram_offset
:
0x0000
,
tiles
:
[
Tile
{
buffer
:
[
0u8
;
64
]
};
TILE_COUNT
],
obj_data
:
[
ObjectData
{
x
:
0
,
...
...
@@ -420,8 +456,10 @@ impl Ppu {
pub
fn
reset
(
&
mut
self
)
{
self
.color_buffer
=
Box
::
new
([
0u8
;
COLOR_BUFFER_SIZE
]);
self
.frame_buffer
=
Box
::
new
([
0u8
;
FRAME_BUFFER_SIZE
]);
self
.vram
=
[
0u8
;
VRAM_SIZE
];
self
.vram
=
[
0u8
;
VRAM_SIZE
_CGB
];
self
.hram
=
[
0u8
;
HRAM_SIZE
];
self
.vram_bank
=
0x0
;
self
.vram_offset
=
0x0000
;
self
.tiles
=
[
Tile
{
buffer
:
[
0u8
;
64
]
};
TILE_COUNT
];
self
.palette
=
[[
0u8
;
RGB_SIZE
];
PALETTE_SIZE
];
self
.palette_obj_0
=
[[
0u8
;
RGB_SIZE
];
PALETTE_SIZE
];
...
...
@@ -544,7 +582,7 @@ impl Ppu {
pub
fn
read
(
&
mut
self
,
addr
:
u16
)
->
u8
{
match
addr
{
0x8000
..=
0x9fff
=>
self
.vram
[(
addr
&
0x1fff
)
as
usize
],
0x8000
..=
0x9fff
=>
self
.vram
[
(
self
.vram_offset
+
(
addr
&
0x1fff
)
)
as
usize
],
0xfe00
..=
0xfe9f
=>
self
.oam
[(
addr
&
0x009f
)
as
usize
],
0xff80
..=
0xfffe
=>
self
.hram
[(
addr
&
0x007f
)
as
usize
],
0xff40
=>
...
...
@@ -577,7 +615,7 @@ impl Ppu {
0xff4a
=>
self
.wy
,
0xff4b
=>
self
.wx
,
// 0xFF4F — VBK (CGB only)
0xff4f
=>
0xf
f
,
0xff4f
=>
self
.vram_bank
|
0xf
e
,
// 0xFF68 — BCPS/BGPI (CGB only)
0xff68
=>
self
.palette_address_bg
|
if
self
.auto_increment_bg
{
0x80
}
else
{
0x00
},
// 0xFF69 — BCPD/BGPD (CGB only)
...
...
@@ -596,7 +634,7 @@ impl Ppu {
pub
fn
write
(
&
mut
self
,
addr
:
u16
,
value
:
u8
)
{
match
addr
{
0x8000
..=
0x9fff
=>
{
self
.vram
[(
addr
&
0x1fff
)
as
usize
]
=
value
;
self
.vram
[
(
self
.vram_offset
+
(
addr
&
0x1fff
)
)
as
usize
]
=
value
;
if
addr
<
0x9800
{
self
.update_tile
(
addr
,
value
);
}
...
...
@@ -653,7 +691,10 @@ impl Ppu {
0xff4a
=>
self
.wy
=
value
,
0xff4b
=>
self
.wx
=
value
,
// 0xFF4F — VBK (CGB only)
0xff4f
=>
(),
0xff4f
=>
{
self
.vram_bank
=
value
&
0x01
;
self
.vram_offset
=
self
.vram_bank
as
u16
*
0x2000
;
}
// 0xFF68 — BCPS/BGPI (CGB only)
0xff68
=>
{
self
.palette_address_bg
=
value
&
0x3f
;
...
...
@@ -786,7 +827,7 @@ impl Ppu {
/// just been written to a location on the VRAM associated
/// with tiles.
fn
update_tile
(
&
mut
self
,
addr
:
u16
,
_value
:
u8
)
{
let
addr
=
(
addr
&
0x1ffe
)
as
usize
;
let
addr
=
(
self
.vram_offset
+
(
addr
&
0x1ffe
)
)
as
usize
;
let
tile_index
=
(
addr
>>
4
)
&
0x01ff
;
let
tile
=
self
.tiles
[
tile_index
]
.borrow_mut
();
let
y
=
(
addr
>>
1
)
&
0x0007
;
...
...
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment