84 lines
1.8 KiB
Go
84 lines
1.8 KiB
Go
package gb
|
|
|
|
import (
|
|
"fmt"
|
|
)
|
|
|
|
// 0x0000 - 0x3FFF : ROM Bank 0
|
|
// 0x4000 - 0x7FFF : ROM Bank 1 - Switchable
|
|
// 0x8000 - 0x97FF : CHR RAM
|
|
// 0x9800 - 0x9BFF : BG Map 1
|
|
// 0x9C00 - 0x9FFF : BG Map 2
|
|
// 0xA000 - 0xBFFF : Cartridge RAM
|
|
// 0xC000 - 0xCFFF : RAM Bank 0
|
|
// 0xD000 - 0xDFFF : RAM Bank 1-7 - switchable - Color only
|
|
// 0xE000 - 0xFDFF : Reserved - Echo RAM
|
|
// 0xFE00 - 0xFE9F : Object Attribute Memory
|
|
// 0xFEA0 - 0xFEFF : Reserved - Unusable
|
|
// 0xFF00 - 0xFF7F : I/O Registers
|
|
// 0xFF80 - 0xFFFE : Zero Page
|
|
|
|
type Bus struct {
|
|
Cart *Cartridge
|
|
RAM *RAM
|
|
}
|
|
|
|
func NewBus(cart *Cartridge) *Bus {
|
|
bus := Bus{Cart: cart, RAM: NewRAM()}
|
|
|
|
return &bus
|
|
}
|
|
|
|
func (bus *Bus) Read(address uint16) byte {
|
|
if address < 0x8000 {
|
|
// ROM data
|
|
value, err := bus.Cart.Read(address)
|
|
if err != nil {
|
|
fmt.Printf("Error reading from bus address %X: %s", address, err)
|
|
return 0
|
|
}
|
|
return value
|
|
} else if address < 0xE000 {
|
|
return bus.RAM.WRAMRead(address)
|
|
} else {
|
|
fmt.Printf("Reading from bus address %X not implemented!\n", address)
|
|
return 0
|
|
}
|
|
}
|
|
|
|
func (bus *Bus) Read16(address uint16) uint16 {
|
|
lo := bus.Read(address)
|
|
hi := bus.Read(address + 1)
|
|
|
|
return uint16(lo) | uint16(hi)<<8
|
|
}
|
|
|
|
func (bus *Bus) Write(address uint16, value byte) error {
|
|
if address < 0x8000 {
|
|
// ROM data
|
|
err := bus.Cart.Write(address, value)
|
|
if err != nil {
|
|
return fmt.Errorf("Error writing to bus address %X: %s", address, err)
|
|
}
|
|
return nil
|
|
} else if address < 0xE000 {
|
|
bus.RAM.WRAMWrite(address, value)
|
|
return nil
|
|
} else {
|
|
return fmt.Errorf("Writing to bus address %X not implemented!", address)
|
|
}
|
|
}
|
|
|
|
func (bus *Bus) Write16(address uint16, value uint16) error {
|
|
err := bus.Write(address+1, byte((value>>8)&0xFF))
|
|
if err != nil {
|
|
return err
|
|
}
|
|
err = bus.Write(address, byte(value&0xFF))
|
|
if err != nil {
|
|
return err
|
|
}
|
|
|
|
return nil
|
|
}
|