Minor progress on gb_ppu_render_continue
This commit is contained in:
parent
feb59859ef
commit
4fe5bd2e15
14
include/gb.h
14
include/gb.h
|
@ -25,7 +25,7 @@ typedef struct gb_timers_t {
|
|||
} GBTimers;
|
||||
|
||||
GBTimers *gb_timers_open(RIO *io);
|
||||
void gb_timers_update(GBTimers *timers, ut32 cycles);
|
||||
void gb_timers_continue(GBTimers *timers, ut32 cycles);
|
||||
void gb_timers_close(GBTimers *timers, RIO *io);
|
||||
|
||||
typedef struct gb_joypad_t {
|
||||
|
@ -44,7 +44,7 @@ typedef struct gb_joypad_t {
|
|||
} GBJoypad;
|
||||
|
||||
GBJoypad *gb_joypad_open(RIO *io);
|
||||
void gb_joypad_update(GBJoypad *joypad);
|
||||
void gb_joypad_continue(GBJoypad *joypad);
|
||||
void gb_joypad_close(GBJoypad *joypad, RIO *io);
|
||||
|
||||
typedef struct gb_dma_t {
|
||||
|
@ -69,7 +69,7 @@ typedef struct gb_dma_t {
|
|||
|
||||
GBDMA *gb_dma_open(RIO *io);
|
||||
//void gb_dma_enable_cgb(GBDMA *dma);
|
||||
void gb_dma_update(GBDMA *dma, RIO *io, ut32 cycles, bool pre_exec);
|
||||
void gb_dma_continue(GBDMA *dma, RIO *io, ut32 cycles, bool pre_exec);
|
||||
void gb_dma_close(GBDMA *dma, RIO *io);
|
||||
|
||||
enum {
|
||||
|
@ -121,6 +121,8 @@ typedef struct pixel_fifo_fetcher_t {
|
|||
#define GB_PIXEL_FIFO_FETCH_OBJECT 0x10
|
||||
#define GB_PIXEL_FIFO_FETCH_WINDOW 0x20
|
||||
#define GB_PIXEL_FIFO_FETCH_READY 0x40
|
||||
//specifies if scx & 0x7 and wy are copied into fifo
|
||||
#define GB_PIXEL_FIFO_REG_DATA_LOADED 0x80
|
||||
|
||||
#define GB_OAM_PALLET 0x10
|
||||
#define GB_OAM_FLIP_X 0x20
|
||||
|
@ -132,6 +134,7 @@ typedef struct pixel_fifo_fetcher_t {
|
|||
#define GB_FIFO_OAM_FLIP_Y (GB_OAM_FLIP_Y << 24)
|
||||
#define GB_FIFO_OAM_PRIORITY (GB_OAM_PRIORITY << 24)
|
||||
|
||||
|
||||
typedef struct pixel_fifo_t {
|
||||
ut64 data;
|
||||
PixelFifoFetcher fetcher[2];
|
||||
|
@ -149,8 +152,9 @@ obj p1 - 11
|
|||
ut8 flags;
|
||||
};
|
||||
ut8 n_fpixel; //number of pixel that are currently in the fifo
|
||||
ut8 wy;
|
||||
ut8 x;
|
||||
ut8 wy;
|
||||
ut8 dx; //discard x
|
||||
} PixelFifo;
|
||||
|
||||
typedef struct gb_dmg_ppu_t {
|
||||
|
@ -178,7 +182,7 @@ typedef struct gameboy_t {
|
|||
} GB;
|
||||
|
||||
GBPPU *gb_ppu_open (RIO *io, SDL_Renderer *renderer);
|
||||
void gb_ppu_update (GB *gb, ut32 cycles);
|
||||
void gb_ppu_continue (GB *gb, ut32 cycles);
|
||||
void gb_ppu_close (GBPPU *ppu, RIO *io);
|
||||
|
||||
extern RIOPlugin r_io_plugin_gb_timers;
|
||||
|
|
2
io/dma.c
2
io/dma.c
|
@ -221,7 +221,7 @@ GBDMA *gb_dma_open (RIO *io) {
|
|||
return dma;
|
||||
}
|
||||
|
||||
void gb_dma_update (GBDMA *dma, RIO *io, ut32 cycles, bool pre_exec) {
|
||||
void gb_dma_continue (GBDMA *dma, RIO *io, ut32 cycles, bool pre_exec) {
|
||||
if (!(dma->seek & GB_DMA_ACTIVE)) {
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -108,7 +108,7 @@ GBJoypad *gb_joypad_open (RIO *io) {
|
|||
return joypad;
|
||||
}
|
||||
|
||||
void gb_joypad_update(GBJoypad *joypad) {
|
||||
void gb_joypad_continue(GBJoypad *joypad) {
|
||||
joypad->odata &= 0xc0;
|
||||
joypad->odata |= joypad->data & 0x3f;
|
||||
SDL_PumpEvents ();
|
||||
|
|
60
io/ppu.c
60
io/ppu.c
|
@ -124,7 +124,7 @@ GBPPU *gb_ppu_open (RIO *io, SDL_Renderer *renderer) {
|
|||
return ppu;
|
||||
}
|
||||
|
||||
static ut32 gb_ppu_oam_scan_update (GB *gb, ut32 cycles) {
|
||||
static ut32 gb_ppu_oam_scan_continue (GB *gb, ut32 cycles) {
|
||||
if (gb->ppu->ost.addr >= 0xa0) {
|
||||
gb->ppu->ost.addr = 0;
|
||||
gb->ppu->ost.n_entries = 0;
|
||||
|
@ -279,6 +279,9 @@ static void gb_pixel_fifo_fetch_continue (GB *gb) {
|
|||
}
|
||||
}
|
||||
case 5:
|
||||
if (!fetch_obj) {
|
||||
fifo->flags |= GB_PIXEL_FIFO_FETCH_READY;
|
||||
}
|
||||
break;
|
||||
case 6:
|
||||
if (fetch_obj) {
|
||||
|
@ -311,37 +314,74 @@ static void gb_pixel_fifo_fetch_continue (GB *gb) {
|
|||
}
|
||||
break;
|
||||
case 7:
|
||||
fifo->flags |= GB_PIXEL_FIFO_FETCH_READY;
|
||||
if (fetch_obj) {
|
||||
fifo->flags |= GB_PIXEL_FIFO_FETCH_READY;
|
||||
}
|
||||
}
|
||||
fifo->fetcher[fetch_obj].state_ctr = (fifo->fetcher[fetch_obj].state_ctr + 1) & 0x7;
|
||||
}
|
||||
|
||||
static ut32 gb_ppu_render_update (GB *gb, ut32 cycles) {
|
||||
static void gb_ppu_render_launch (GB *gb) {
|
||||
RIOMap *vram = r_io_map_get (gb->io, gb->ppu->vram_mapid);
|
||||
vram->perm = 0; //disable vram access for rendering
|
||||
gb->ppu->fifo = (const PixelFifo){0};
|
||||
gb->ppu->fifo.remaining_cycles = 376;
|
||||
}
|
||||
|
||||
static ut32 gb_ppu_render_continue (GB *gb, ut32 cycles) {
|
||||
PixelFifo *fifo = &gb->ppu->fifo;
|
||||
if (R_UNLIKELY (!(fifo->flags & GB_PIXEL_FIFO_REG_DATA_LOADED))) {
|
||||
fifo->dx = gb->ppu->buf[GB_PPU_SCX] & 0x7;
|
||||
fifo->wy = gb->ppu->buf[GB_PPU_WY];
|
||||
fifo->flags |= GB_PIXEL_FIFO_REG_DATA_LOADED;
|
||||
}
|
||||
while (cycles) {
|
||||
if (fifo->n_fpixel < 9) {
|
||||
gb_pixel_fifo_fetch_continue (gb);
|
||||
if (fifo->flags & GB_PIXEL_FIFO_FETCH_READY) {
|
||||
if (!fifo->n_fpixel) {
|
||||
fifo->data = ((ut64)fifo->fetcher[0].fetched) << 32;
|
||||
} else {
|
||||
fifo->data |= fifo->fetcher[0].fetched;
|
||||
}
|
||||
fifo->n_fpixel += 8;
|
||||
//I suspect the initial 16 pixels fetch on each line only takes 12 cycles instead of 16,
|
||||
//because the pixel fifo is empty
|
||||
fifo->flags ^= GB_PIXEL_FIFO_FETCH_READY;
|
||||
fifo->fetcher[0].state_ctr = 0;
|
||||
}
|
||||
}
|
||||
fifo->remaining_cycles--;
|
||||
cycles--;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static ut32 gb_ppu_hblank_update (GB *gb, ut32 cycles) {
|
||||
static ut32 gb_ppu_hblank_continue (GB *gb, ut32 cycles) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
static ut32 gb_ppu_vblank_update (GB *gb, ut32 cycles) {
|
||||
static ut32 gb_ppu_vblank_continue (GB *gb, ut32 cycles) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void gb_ppu_update (GB *gb, ut32 cycles) {
|
||||
void gb_ppu_continue (GB *gb, ut32 cycles) {
|
||||
while (cycles) {
|
||||
switch (gb->ppu->buf[GB_PPU_STAT] & GB_PPU_STAT_MODE_MASK) {
|
||||
case GB_PPU_STAT_MODE_OAM_SCAN:
|
||||
cycles = gb_ppu_oam_scan_update (gb, cycles);
|
||||
cycles = gb_ppu_oam_scan_continue (gb, cycles);
|
||||
if ((gb->ppu->buf[GB_PPU_STAT] & GB_PPU_STAT_MODE_MASK) == GB_PPU_STAT_MODE_RENDER) {
|
||||
gb_ppu_render_launch (gb);
|
||||
}
|
||||
break;
|
||||
case GB_PPU_STAT_MODE_RENDER:
|
||||
cycles = gb_ppu_render_update (gb, cycles);
|
||||
cycles = gb_ppu_render_continue (gb, cycles);
|
||||
break;
|
||||
case GB_PPU_STAT_MODE_HBLANK:
|
||||
cycles = gb_ppu_hblank_update (gb, cycles);
|
||||
cycles = gb_ppu_hblank_continue (gb, cycles);
|
||||
break;
|
||||
case GB_PPU_STAT_MODE_VBLANK:
|
||||
cycles = gb_ppu_vblank_update (gb, cycles);
|
||||
cycles = gb_ppu_vblank_continue (gb, cycles);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -130,7 +130,7 @@ void gb_timers_close (GBTimers *timers, RIO *io) {
|
|||
free (timers);
|
||||
}
|
||||
|
||||
void gb_timers_update (GBTimers *timers, ut32 cycles) {
|
||||
void gb_timers_continue (GBTimers *timers, ut32 cycles) {
|
||||
bool request_interrupt = false;
|
||||
do {
|
||||
//ensure all falling edges are detected
|
||||
|
|
Loading…
Reference in New Issue
Block a user