diff --git a/core/vb.c b/core/vb.c index 165a1af..fb34d83 100644 --- a/core/vb.c +++ b/core/vb.c @@ -121,6 +121,7 @@ struct VB { uint32_t fbSrc; /* Source frame buffer address */ int32_t repeat; /* Current column table repeat value */ int step; /* Processing phase */ + uint32_t until; /* Clocks until interrupt condition */ } dp; /* Pixel processor */ diff --git a/core/vip.c b/core/vip.c index 2d3f319..b97201c 100644 --- a/core/vip.c +++ b/core/vip.c @@ -382,16 +382,18 @@ static int vipOnFrame(VB *sim) { static int vipEmulateDisplay(VB *sim, uint32_t clocks) { /* Process all clocks */ - while (clocks != 0) { + for (;;) { /* The next event is after the time remaining */ if (sim->vip.dp.clocks > clocks) { sim->vip.dp.clocks -= clocks; + sim->vip.dp.until -= clocks; return 0; } /* Advance forward the component's number of clocks */ clocks -= sim->vip.dp.clocks; + sim->vip.dp.until -= sim->vip.dp.clocks; sim->vip.dp.clocks = 0; /* Processing by operation phase */ @@ -401,6 +403,7 @@ static int vipEmulateDisplay(VB *sim, uint32_t clocks) { sim->vip.dp.clocks = vipClocksMs(3); sim->vip.dp.fclk = 1; sim->vip.dp.step = 1; + sim->vip.dp.until = vipClocksMs(8); vipThrow(sim, 0x0010); /* FRAMESTART */ /* TODO: Initiate drawing, throw GAMESTART */ /* ELSE: Set OVERTIME, throw TIMEERR */ @@ -437,6 +440,7 @@ static int vipEmulateDisplay(VB *sim, uint32_t clocks) { else sim->vip.dp.l1bsy = 0; sim->vip.dp.clocks = vipClocksMs(2); sim->vip.dp.step = 4; + sim->vip.dp.until = vipClocksMs(10); vipThrow(sim, 0x0002); /* LFBEND */ break; @@ -460,10 +464,14 @@ static int vipEmulateDisplay(VB *sim, uint32_t clocks) { /* Fallthrough */ case 6: /* 13ms-18ms - Display right frame buffer */ + if ((sim->vip.dp.column & 3) == 0) + vipComputeBrightness(sim); vipTransferColumn(sim, 1); sim->vip.dp.clocks = 260 + (0xA94 >> sim->vip.dp.column % 12 & 1); sim->vip.dp.column++; + if ((sim->vip.dp.column & 3) == 0) + sim->vip.dp.cta -= 2; if (sim->vip.dp.column == 384) sim->vip.dp.step = 7; break; @@ -474,6 +482,7 @@ static int vipEmulateDisplay(VB *sim, uint32_t clocks) { else sim->vip.dp.r1bsy = 0; sim->vip.dp.clocks = vipClocksMs(2); sim->vip.dp.step = 0; + sim->vip.dp.until = vipClocksMs(2); vipThrow(sim, 0x0004); /* RFBEND */ if (vipOnFrame(sim)) return 1; @@ -587,8 +596,8 @@ static void vipReset(VB *sim) { /* Determine how many clocks are guaranteed to process */ static uint32_t vipUntil(VB *sim, uint32_t clocks) { - (void) sim; - /* Don't allow clocks to exceed interrupt conditions, even if disabled */ + if (clocks > sim->vip.dp.until) + clocks = sim->vip.dp.until; return clocks; }