comparison vdp.c @ 718:eaba6789f316

Update vscroll latch implementation to be more in line with what Eke-Eke has observed. Revert the change to vdp_cycles_to_line because it breaks hints on line 0. H-Int timing is still a little messed up, but the previous change made things worse.
author Michael Pavone <pavone@retrodev.com>
date Wed, 20 May 2015 10:35:03 -0700
parents 22dbdf50d33c
children 019d27995e32
comparison
equal deleted inserted replaced
717:22dbdf50d33c 718:eaba6789f316
485 write_cram(context, start->address, start->partial == 2 ? context->fifo[context->fifo_write].value : start->value); 485 write_cram(context, start->address, start->partial == 2 ? context->fifo[context->fifo_write].value : start->value);
486 break; 486 break;
487 } 487 }
488 case VSRAM_WRITE: 488 case VSRAM_WRITE:
489 if (((start->address/2) & 63) < VSRAM_SIZE) { 489 if (((start->address/2) & 63) < VSRAM_SIZE) {
490 //printf("VSRAM Write: %X to %X\n", start->value, context->address); 490 //printf("VSRAM Write: %X to %X @ vcounter: %d, hslot: %d, cycle: %d\n", start->value, context->address, context->vcounter, context->hslot, context->cycles);
491 context->vsram[(start->address/2) & 63] = start->partial == 2 ? context->fifo[context->fifo_write].value : start->value; 491 context->vsram[(start->address/2) & 63] = start->partial == 2 ? context->fifo[context->fifo_write].value : start->value;
492 } 492 }
493 493
494 break; 494 break;
495 } 495 }
657 } 657 }
658 if (context->double_res) { 658 if (context->double_res) {
659 vscroll <<= 1; 659 vscroll <<= 1;
660 vscroll |= 1; 660 vscroll |= 1;
661 } 661 }
662 //TODO: Further research on vscroll latch behavior and the "first column bug" seen in Gynoug 662 //TODO: Further research on vscroll latch behavior and the "first column bug"
663 //this should be close, but won't match the exact behavior Eke-Eke has written about 663 if (!column) {
664 if (column == 2 || (column && (context->regs[REG_MODE_3] & BIT_VSCROLL))) { 664 if (context->regs[REG_MODE_3] & BIT_VSCROLL) {
665 if (context->regs[REG_MODE_4] & BIT_H40) {
666 //Based on observed behavior documented by Eke-Eke, I'm guessing the VDP
667 //ends up fetching the last value on the VSRAM bus in the H40 case
668 //getting the last latched value should be close enough for now
669 if (!vsram_off) {
670 context->vscroll_latch[0] = context->vscroll_latch[1];
671 }
672 } else {
673 //supposedly it's always forced to 0 in the H32 case
674 context->vscroll_latch[0] = context->vscroll_latch[1] = 0;
675 }
676 } else {
677 context->vscroll_latch[vsram_off] = context->vsram[vsram_off];
678 }
679 } else if (context->regs[REG_MODE_3] & BIT_VSCROLL) {
665 context->vscroll_latch[vsram_off] = context->vsram[column - 2 + vsram_off]; 680 context->vscroll_latch[vsram_off] = context->vsram[column - 2 + vsram_off];
666 } 681 }
667 vscroll &= context->vscroll_latch[vsram_off] + line; 682 vscroll &= context->vscroll_latch[vsram_off] + line;
668 context->v_offset = vscroll & v_offset_mask; 683 context->v_offset = vscroll & v_offset_mask;
669 //printf("%s | line %d, vsram: %d, vscroll: %d, v_offset: %d\n",(vsram_off ? "B" : "A"), line, context->vsram[context->regs[REG_MODE_3] & 0x4 ? column : 0], vscroll, context->v_offset); 684 //printf("%s | line %d, vsram: %d, vscroll: %d, v_offset: %d\n",(vsram_off ? "B" : "A"), line, context->vsram[context->regs[REG_MODE_3] & 0x4 ? column : 0], vscroll, context->v_offset);
1662 context->hv_latch = vdp_hv_counter_read(context); 1677 context->hv_latch = vdp_hv_counter_read(context);
1663 } 1678 }
1664 if (reg == REG_BG_COLOR) { 1679 if (reg == REG_BG_COLOR) {
1665 value &= 0x3F; 1680 value &= 0x3F;
1666 } 1681 }
1667 if (reg == REG_MODE_4 && ((value ^ context->regs[reg]) & BIT_H40)) { 1682 /*if (reg == REG_MODE_4 && ((value ^ context->regs[reg]) & BIT_H40)) {
1668 printf("Mode changed from H%d to H%d @ %d, frame: %d\n", context->regs[reg] & BIT_H40 ? 40 : 32, value & BIT_H40 ? 40 : 32, context->cycles, context->frame); 1683 printf("Mode changed from H%d to H%d @ %d, frame: %d\n", context->regs[reg] & BIT_H40 ? 40 : 32, value & BIT_H40 ? 40 : 32, context->cycles, context->frame);
1669 } 1684 }*/
1670 context->regs[reg] = value; 1685 context->regs[reg] = value;
1671 if (reg == REG_MODE_4) { 1686 if (reg == REG_MODE_4) {
1672 context->double_res = (value & (BIT_INTERLACE | BIT_DOUBLE_RES)) == (BIT_INTERLACE | BIT_DOUBLE_RES); 1687 context->double_res = (value & (BIT_INTERLACE | BIT_DOUBLE_RES)) == (BIT_INTERLACE | BIT_DOUBLE_RES);
1673 if (!context->double_res) { 1688 if (!context->double_res) {
1674 context->framebuf = context->oddbuf; 1689 context->framebuf = context->oddbuf;
1950 } else { 1965 } else {
1951 lines = jump_start - context->vcounter + target - jump_dst; 1966 lines = jump_start - context->vcounter + target - jump_dst;
1952 } 1967 }
1953 } else { 1968 } else {
1954 if (context->vcounter < jump_start) { 1969 if (context->vcounter < jump_start) {
1955 lines = jump_start - context->vcounter + 512 - jump_dst + 1; 1970 lines = jump_start - context->vcounter + 512 - jump_dst;
1956 } else { 1971 } else {
1957 lines = 512 - context->vcounter + 1; 1972 lines = 512 - context->vcounter;
1958 } 1973 }
1959 if (target < jump_start) { 1974 if (target < jump_start) {
1960 lines += target; 1975 lines += target;
1961 } else { 1976 } else {
1962 lines += jump_start + target - jump_dst; 1977 lines += jump_start + target - jump_dst;