Mercurial > repos > blastem
comparison vdp.c @ 1333:69c25e1188e5
Small tweak to how SAT cache updates are done. Mostly fixes the rotating cube scene in Overdrive 2
author | Michael Pavone <pavone@retrodev.com> |
---|---|
date | Wed, 26 Apr 2017 22:16:12 -0700 |
parents | 9bba5ff5beb8 |
children | 7757d605e365 |
comparison
equal
deleted
inserted
replaced
1332:87bbc4bec958 | 1333:69c25e1188e5 |
---|---|
802 context->flags &= ~FLAG_DMA_RUN; | 802 context->flags &= ~FLAG_DMA_RUN; |
803 context->cd &= 0xF; | 803 context->cd &= 0xF; |
804 } | 804 } |
805 } | 805 } |
806 | 806 |
807 void write_vram_word(vdp_context *context, uint32_t address, uint8_t value) | 807 static void vdp_check_update_sat(vdp_context *context, uint32_t address, uint16_t value) |
808 { | 808 { |
809 if (!(address & 4)) { | 809 if (context->regs[REG_MODE_2] & BIT_MODE_5) { |
810 uint32_t sat_address = mode5_sat_address(context); | 810 if (!(address & 4)) { |
811 if(address >= sat_address && address < (sat_address + SAT_CACHE_SIZE*2)) { | 811 uint32_t sat_address = mode5_sat_address(context); |
812 uint16_t cache_address = address - sat_address; | 812 if(address >= sat_address && address < (sat_address + SAT_CACHE_SIZE*2)) { |
813 cache_address = (cache_address & 3) | (cache_address >> 1 & 0x1FC); | 813 uint16_t cache_address = address - sat_address; |
814 context->sat_cache[cache_address] = value >> 8; | 814 cache_address = (cache_address & 3) | (cache_address >> 1 & 0x1FC); |
815 context->sat_cache[cache_address^1] = value; | 815 context->sat_cache[cache_address] = value >> 8; |
816 } | 816 context->sat_cache[cache_address^1] = value; |
817 } | 817 } |
818 address = (address & 0x3FC) | (address >> 1 & 0xFC01) | (address >> 9 & 0x2); | 818 } |
819 address ^= 1; | 819 } |
820 //TODO: Support an option to actually have 128KB of VRAM | 820 } |
821 context->vdpmem[address] = value; | 821 |
822 } | 822 void vdp_check_update_sat_byte(vdp_context *context, uint32_t address, uint8_t value) |
823 | |
824 void write_vram_byte(vdp_context *context, uint32_t address, uint8_t value) | |
825 { | 823 { |
826 if (context->regs[REG_MODE_2] & BIT_MODE_5) { | 824 if (context->regs[REG_MODE_2] & BIT_MODE_5) { |
827 if (!(address & 4)) { | 825 if (!(address & 4)) { |
828 uint32_t sat_address = mode5_sat_address(context); | 826 uint32_t sat_address = mode5_sat_address(context); |
829 if(address >= sat_address && address < (sat_address + SAT_CACHE_SIZE*2)) { | 827 if(address >= sat_address && address < (sat_address + SAT_CACHE_SIZE*2)) { |
830 uint16_t cache_address = address - sat_address; | 828 uint16_t cache_address = address - sat_address; |
831 cache_address = (cache_address & 3) | (cache_address >> 1 & 0x1FC); | 829 cache_address = (cache_address & 3) | (cache_address >> 1 & 0x1FC); |
832 context->sat_cache[cache_address] = value; | 830 context->sat_cache[cache_address] = value; |
833 } | 831 } |
834 } | 832 } |
833 } | |
834 } | |
835 | |
836 static void write_vram_word(vdp_context *context, uint32_t address, uint16_t value) | |
837 { | |
838 address = (address & 0x3FC) | (address >> 1 & 0xFC01) | (address >> 9 & 0x2); | |
839 address ^= 1; | |
840 //TODO: Support an option to actually have 128KB of VRAM | |
841 context->vdpmem[address] = value; | |
842 } | |
843 | |
844 static void write_vram_byte(vdp_context *context, uint32_t address, uint8_t value) | |
845 { | |
846 if (context->regs[REG_MODE_2] & BIT_MODE_5) { | |
835 address &= 0xFFFF; | 847 address &= 0xFFFF; |
836 } else { | 848 } else { |
837 address = mode4_address_map[address & 0x3FFF]; | 849 address = mode4_address_map[address & 0x3FFF]; |
838 } | 850 } |
839 context->vdpmem[address] = value; | 851 context->vdpmem[address] = value; |
852 fifo_entry * start = context->fifo + context->fifo_read; | 864 fifo_entry * start = context->fifo + context->fifo_read; |
853 if (context->fifo_read >= 0 && start->cycle <= context->cycles) { | 865 if (context->fifo_read >= 0 && start->cycle <= context->cycles) { |
854 switch (start->cd & 0xF) | 866 switch (start->cd & 0xF) |
855 { | 867 { |
856 case VRAM_WRITE: | 868 case VRAM_WRITE: |
857 //TODO: Support actually having 128K VRAM as an option | |
858 if ((context->regs[REG_MODE_2] & (BIT_128K_VRAM|BIT_MODE_5)) == (BIT_128K_VRAM|BIT_MODE_5)) { | 869 if ((context->regs[REG_MODE_2] & (BIT_128K_VRAM|BIT_MODE_5)) == (BIT_128K_VRAM|BIT_MODE_5)) { |
870 vdp_check_update_sat(context, start->address, start->value); | |
859 write_vram_word(context, start->address, start->value); | 871 write_vram_word(context, start->address, start->value); |
860 } else if (start->partial) { | 872 } else if (start->partial) { |
861 //printf("VRAM Write: %X to %X at %d (line %d, slot %d)\n", start->value, start->address ^ 1, context->cycles, context->cycles/MCLKS_LINE, (context->cycles%MCLKS_LINE)/16); | 873 //printf("VRAM Write: %X to %X at %d (line %d, slot %d)\n", start->value, start->address ^ 1, context->cycles, context->cycles/MCLKS_LINE, (context->cycles%MCLKS_LINE)/16); |
862 write_vram_byte(context, start->address ^ 1, start->partial == 2 ? start->value >> 8 : start->value); | 874 uint8_t byte = start->partial == 2 ? start->value >> 8 : start->value; |
875 if (start->partial > 1) { | |
876 vdp_check_update_sat_byte(context, start->address ^ 1, byte); | |
877 } | |
878 write_vram_byte(context, start->address ^ 1, byte); | |
863 } else { | 879 } else { |
864 //printf("VRAM Write High: %X to %X at %d (line %d, slot %d)\n", start->value >> 8, start->address, context->cycles, context->cycles/MCLKS_LINE, (context->cycles%MCLKS_LINE)/16); | 880 //printf("VRAM Write High: %X to %X at %d (line %d, slot %d)\n", start->value >> 8, start->address, context->cycles, context->cycles/MCLKS_LINE, (context->cycles%MCLKS_LINE)/16); |
881 vdp_check_update_sat(context, start->address, start->value); | |
865 write_vram_byte(context, start->address, start->value >> 8); | 882 write_vram_byte(context, start->address, start->value >> 8); |
866 start->partial = 1; | 883 start->partial = 1; |
867 //skip auto-increment and removal of entry from fifo | 884 //skip auto-increment and removal of entry from fifo |
868 return; | 885 return; |
869 } | 886 } |
870 break; | 887 break; |
871 case CRAM_WRITE: { | 888 case CRAM_WRITE: { |
872 //printf("CRAM Write | %X to %X\n", start->value, (start->address/2) & (CRAM_SIZE-1)); | 889 //printf("CRAM Write | %X to %X\n", start->value, (start->address/2) & (CRAM_SIZE-1)); |
873 if (start->partial == 1) { | 890 if (start->partial == 3) { |
874 uint16_t val; | 891 uint16_t val; |
875 if ((start->address & 1) && (context->regs[REG_MODE_2] & BIT_MODE_5)) { | 892 if ((start->address & 1) && (context->regs[REG_MODE_2] & BIT_MODE_5)) { |
876 val = (context->cram[start->address >> 1 & (CRAM_SIZE-1)] & 0xFF) | start->value << 8; | 893 val = (context->cram[start->address >> 1 & (CRAM_SIZE-1)] & 0xFF) | start->value << 8; |
877 } else { | 894 } else { |
878 uint16_t address = (context->regs[REG_MODE_2] & BIT_MODE_5) ? start->address >> 1 & (CRAM_SIZE-1) : start->address & 0x1F; | 895 uint16_t address = (context->regs[REG_MODE_2] & BIT_MODE_5) ? start->address >> 1 & (CRAM_SIZE-1) : start->address & 0x1F; |
885 break; | 902 break; |
886 } | 903 } |
887 case VSRAM_WRITE: | 904 case VSRAM_WRITE: |
888 if (((start->address/2) & 63) < VSRAM_SIZE) { | 905 if (((start->address/2) & 63) < VSRAM_SIZE) { |
889 //printf("VSRAM Write: %X to %X @ vcounter: %d, hslot: %d, cycle: %d\n", start->value, context->address, context->vcounter, context->hslot, context->cycles); | 906 //printf("VSRAM Write: %X to %X @ vcounter: %d, hslot: %d, cycle: %d\n", start->value, context->address, context->vcounter, context->hslot, context->cycles); |
890 if (start->partial == 1) { | 907 if (start->partial == 3) { |
891 if (start->address & 1) { | 908 if (start->address & 1) { |
892 context->vsram[(start->address/2) & 63] &= 0xFF; | 909 context->vsram[(start->address/2) & 63] &= 0xFF; |
893 context->vsram[(start->address/2) & 63] |= start->value << 8; | 910 context->vsram[(start->address/2) & 63] |= start->value << 8; |
894 } else { | 911 } else { |
895 context->vsram[(start->address/2) & 63] &= 0xFF00; | 912 context->vsram[(start->address/2) & 63] &= 0xFF00; |
2742 if (context->regs[REG_MODE_2] & BIT_MODE_5) { | 2759 if (context->regs[REG_MODE_2] & BIT_MODE_5) { |
2743 cur->cd = context->cd; | 2760 cur->cd = context->cd; |
2744 } else { | 2761 } else { |
2745 cur->cd = (context->cd & 2) | 1; | 2762 cur->cd = (context->cd & 2) | 1; |
2746 } | 2763 } |
2747 cur->partial = 1; | 2764 cur->partial = 3; |
2748 if (context->fifo_read < 0) { | 2765 if (context->fifo_read < 0) { |
2749 context->fifo_read = context->fifo_write; | 2766 context->fifo_read = context->fifo_write; |
2750 } | 2767 } |
2751 context->fifo_write = (context->fifo_write + 1) & (FIFO_SIZE-1); | 2768 context->fifo_write = (context->fifo_write + 1) & (FIFO_SIZE-1); |
2752 increment_address(context); | 2769 increment_address(context); |