Minimal Game Boy Hello World using GBDK-2020 and PyBoy
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 

4.3 KiB

Hardware Game Boy DMG

Capire i vincoli dell'hardware è indispensabile per capire ogni scelta architetturale del codice. Il Game Boy DMG del 1989 è una macchina meravigliosamente vincolata.


CPU: Sharp SM83

Il processore è una via di mezzo tra lo Z80 e l'Intel 8080, con un set di istruzioni ridotto.

Proprietà Valore
Architettura 8-bit (con registri a 16-bit per indirizzi)
Clock ~4.194304 MHz
Moltiplicazione hardware Assente
Divisione hardware Assente
Virgola mobile (FPU) Assente
Stack 16-bit, in HRAM o WRAM
Registri generali A, B, C, D, E, H, L (più F flags)

!!! warning "Niente moltiplicazioni!" Qualsiasi a * b in C viene compilato da SDCC in una subroutine di addizioni ripetute. Su questo hardware, y * 19 può richiedere 20+ cicli di clock. Il codice di MICE! usa esclusivamente potenze di 2 (y << 5) per eliminare questo costo.


Memoria

0x0000 - 0x3FFF  ROM Bank 0     (16 KB, fisso)
0x4000 - 0x7FFF  ROM Bank 1+    (16 KB, switchable via MBC)
0x8000 - 0x9FFF  VRAM           (8 KB)
  0x8000 - 0x97FF  Tile Data    (384 tile × 16 byte = 6144 byte)
  0x9800 - 0x9BFF  BG Map 0     (32×32 tile)
  0x9C00 - 0x9FFF  BG Map 1     (32×32 tile)
0xA000 - 0xBFFF  External RAM   (cartuccia, non usata)
0xC000 - 0xDFFF  WRAM           (8 KB)
0xFE00 - 0xFE9F  OAM            (160 byte = 40 sprite × 4 byte)
0xFF00 - 0xFF7F  I/O Registers
0xFF80 - 0xFFFE  HRAM           (127 byte, velocissima)

!!! info "VRAM e accesso sicuro" La VRAM è accessibile solo durante HBlank o VBlank. GBDK gestisce questo automaticamente tramite la funzione wait_vbl_done() che il game loop chiama ogni frame per sincronizzarsi con il VBlank.


Video: PPU (Pixel Processing Unit)

Parametro Valore
Risoluzione 160×144 pixel
Colori 4 sfumature di grigio (palette software 2bpp)
Tile size 8×8 pixel, 2 bit per pixel
Tile in VRAM 256 (modalità $8000) o 256 (modalità $8800)
Background map 32×32 tile (256×256 px), visibile 20×18
Sprite (OAM) Max 40 totali, max 10 per scanline
Sprite size 8×8 o 8×16 (configurabile via LCDC)
Layer Background + Window + Sprites

Palette Hardware

Il Game Boy non ha "colori" — ha 4 livelli di intensità per layer. Le palette sono configurate via registri:

BGP_REG  = 0b11100100; // BG:    3=Nero, 2=Grigio Sc., 1=Grigio Ch., 0=Bianco
OBP0_REG = 0b11100100; // Sprite palette 0 (topi, cursore)
OBP1_REG = 0b11000000; // Sprite palette 1 (timer HUD - inverte contrasto)

Il bit 0 di ogni sprite in OAM seleziona quale palette usare (S_PALETTE flag).


Audio: APU (Audio Processing Unit)

L'APU del Game Boy ha 4 canali indipendenti, ciascuno controllato da registri hardware mappati in memoria.

Canale Tipo Registri Uso in MICE!
CH1 Square Wave con Sweep NR10–NR14 Arpeggio melodico
CH2 Square Wave NR21–NR24 Melodia principale
CH3 Wave RAM (forma d'onda custom) NR30–NR34 + 0xFF30 Basso
CH4 Noise (LFSR) NR41–NR44 Percussioni + SFX

Frequenza Note

Le note musicali vengono codificate come valori di frequenza nei registri NR_3 (low byte) e NR_4 (high 3 bit):

f_reg = 2048 - (131072 / Hz)

Esempio per C4 (261.63 Hz):

#define N_C4  0x60B   // = 2048 - (131072 / 261.63) ≈ 0x60B

OAM: Object Attribute Memory

Ogni sprite occupa 4 byte nell'OAM:

Byte Contenuto
0 Y position (schermo + 16)
1 X position (schermo + 8)
2 Tile index (in VRAM sprite tiles)
3 Flags (palette, flip X/Y, priorità)

Uno sprite è "nascosto" posizionandolo a coordinate (0, 0) — fuori dall'area visibile (lo schermo inizia a Y=16, X=8 in coordinate OAM assolute).

// Nascondere uno sprite in GBDK
move_sprite(sprite_index, 0, 0);

!!! danger "Limite 10 sprite per scanline" Se più di 10 sprite si trovano sulla stessa riga orizzontale (scanline), gli ultimi vengono semplicemente ignorati dalla PPU. In MICE! i topi sono disposti verticalmente nel labirinto per ridurre la probabilità di conflitti.