--- uae/src/blitter.c 2018/04/24 16:38:39 1.1.1.1 +++ uae/src/blitter.c 2018/04/24 16:39:15 1.1.1.2 @@ -14,6 +14,7 @@ #include "events.h" #include "memory.h" #include "custom.h" +#include "readcpu.h" #include "newcpu.h" #include "blitter.h" #include "blit.h" @@ -32,13 +33,18 @@ static long int bltwait; struct bltinfo blt_info; static UBYTE blit_filltable[256][4][2]; - +ULONG blit_masktable[BLITTER_MAX_WORDS]; +static UWORD blit_trashtable[BLITTER_MAX_WORDS]; enum blitter_states bltstate; void build_blitfilltable(void) { unsigned int d, fillmask; int i; + + for (i = 0; i < BLITTER_MAX_WORDS; i++) + blit_masktable[i] = 0xFFFF; + for (d = 0; d < 256; d++) { for (i = 0; i < 4; i++) { int fc = i & 1; @@ -75,9 +81,11 @@ static void blitter_dofast(void) { int i,j; UBYTE *bltadatpt = 0, *bltbdatpt = 0, *bltcdatpt = 0, *bltddatpt = 0; - UWORD blitahold, blitbhold, bltaold; UBYTE mt = bltcon0 & 0xFF; + blit_masktable[0] = blt_info.bltafwm; + blit_masktable[blt_info.hblitsize - 1] &= blt_info.bltalwm; + if (bltcon0 & 0x800) { bltadatpt = blit_xlateptr(bltapt, (blt_info.hblitsize*2+blt_info.bltamod)*blt_info.vblitsize); bltapt += (blt_info.hblitsize*2+blt_info.bltamod)*blt_info.vblitsize; @@ -98,19 +106,31 @@ static void blitter_dofast(void) if (blitfunc_dofast[mt] && !blitfill) (*blitfunc_dofast[mt])(bltadatpt,bltbdatpt,bltcdatpt,bltddatpt,&blt_info); else { + ULONG blitbhold = blt_info.bltbhold; + ULONG preva = 0, prevb = 0; + /*if (!blitfill) fprintf(stderr, "minterm %x not present\n",mt); */ for (j = 0; j < blt_info.vblitsize; j++) { blitfc = !!(bltcon1 & 0x4); for (i = 0; i < blt_info.hblitsize; i++) { - if (bltadatpt) { blt_info.bltadat = (*bltadatpt << 8) | *(bltadatpt + 1); bltadatpt += 2; } - if (bltbdatpt) { blt_info.bltbdat = (*bltbdatpt << 8) | *(bltbdatpt + 1); bltbdatpt += 2; } - if (bltcdatpt) { blt_info.bltcdat = (*bltcdatpt << 8) | *(bltcdatpt + 1); bltcdatpt += 2; } - bltaold = blt_info.bltadat; - if (i == 0) bltaold &= blt_info.bltafwm; - if (i== blt_info.hblitsize-1) bltaold &= blt_info.bltalwm; - blitahold = (((ULONG)blt_info.blitpreva << 16) | bltaold) >> blt_info.blitashift; - blitbhold = (((ULONG)blt_info.blitprevb << 16) | blt_info.bltbdat) >> blt_info.blitbshift; - blt_info.bltddat = blit_func(blitahold, blitbhold, blt_info.bltcdat, mt); + ULONG bltadat, blitahold; + if (bltadatpt) { + bltadat = do_get_mem_word((UWORD *)bltadatpt); bltadatpt += 2; + } else + bltadat = blt_info.bltadat; + bltadat &= blit_masktable[i]; + blitahold = (((ULONG)preva << 16) | bltadat) >> blt_info.blitashift; + preva = bltadat; + + if (bltbdatpt) { + UWORD bltbdat = do_get_mem_word((UWORD *)bltbdatpt); bltbdatpt += 2; + blitbhold = (((ULONG)prevb << 16) | bltbdat) >> blt_info.blitbshift; + prevb = bltbdat; + } + if (bltcdatpt) { + blt_info.bltcdat = do_get_mem_word((UWORD *)bltcdatpt); bltcdatpt += 2; + } + blt_info.bltddat = blit_func(blitahold, blitbhold, blt_info.bltcdat, mt) & 0xFFFF; if (blitfill) { UWORD d = blt_info.bltddat; int ifemode = blitife ? 2 : 0; @@ -119,16 +139,22 @@ static void blitter_dofast(void) + (blit_filltable[d >> 8][ifemode + fc1][0] << 8)); blitfc = blit_filltable[d >> 8][ifemode + fc1][1]; } - blt_info.blitpreva = bltaold; blt_info.blitprevb = blt_info.bltbdat; if (blt_info.bltddat) blt_info.blitzero = 0; - if (bltddatpt) { *bltddatpt = blt_info.bltddat >> 8; *(bltddatpt+1) = blt_info.bltddat; bltddatpt += 2; } + if (bltddatpt) { + do_put_mem_word((UWORD *)bltddatpt, blt_info.bltddat); + bltddatpt += 2; + } } if (bltadatpt) bltadatpt += blt_info.bltamod; if (bltbdatpt) bltbdatpt += blt_info.bltbmod; if (bltcdatpt) bltcdatpt += blt_info.bltcmod; if (bltddatpt) bltddatpt += blt_info.bltdmod; } + blt_info.bltbhold = blitbhold; } + blit_masktable[0] = 0xFFFF; + blit_masktable[blt_info.hblitsize - 1] = 0xFFFF; + bltstate = BLT_done; } @@ -136,9 +162,11 @@ static void blitter_dofast_desc(void) { int i,j; UBYTE *bltadatpt = 0, *bltbdatpt = 0, *bltcdatpt = 0, *bltddatpt = 0; - UWORD blitahold, blitbhold, bltaold; UBYTE mt = bltcon0 & 0xFF; + blit_masktable[0] = blt_info.bltafwm; + blit_masktable[blt_info.hblitsize - 1] &= blt_info.bltalwm; + if (bltcon0 & 0x800) { bltadatpt = blit_xlateptr_desc(bltapt, (blt_info.hblitsize*2+blt_info.bltamod)*blt_info.vblitsize); bltapt -= (blt_info.hblitsize*2+blt_info.bltamod)*blt_info.vblitsize; @@ -158,19 +186,30 @@ static void blitter_dofast_desc(void) if (blitfunc_dofast_desc[mt] && !blitfill) (*blitfunc_dofast_desc[mt])(bltadatpt,bltbdatpt,bltcdatpt,bltddatpt,&blt_info); else { + ULONG blitbhold = blt_info.bltbhold; + ULONG preva = 0, prevb = 0; + /* if (!blitfill) fprintf(stderr, "minterm %x not present\n",mt);*/ for (j = 0; j < blt_info.vblitsize; j++) { blitfc = !!(bltcon1 & 0x4); for (i = 0; i < blt_info.hblitsize; i++) { - if (bltadatpt) { blt_info.bltadat = (*bltadatpt << 8) | *(bltadatpt + 1); bltadatpt -= 2; } - if (bltbdatpt) { blt_info.bltbdat = (*bltbdatpt << 8) | *(bltbdatpt + 1); bltbdatpt -= 2; } - if (bltcdatpt) { blt_info.bltcdat = (*bltcdatpt << 8) | *(bltcdatpt + 1); bltcdatpt -= 2; } - bltaold = blt_info.bltadat; - if (i == 0) bltaold &= blt_info.bltafwm; - if (i== blt_info.hblitsize-1) bltaold &= blt_info.bltalwm; - blitahold = (((ULONG)bltaold << 16) | blt_info.blitpreva) >> (16-blt_info.blitashift); - blitbhold = (((ULONG)blt_info.bltbdat << 16) | blt_info.blitprevb) >> (16-blt_info.blitbshift); - blt_info.bltddat = blit_func(blitahold, blitbhold, blt_info.bltcdat, mt); + ULONG bltadat, blitahold; + if (bltadatpt) { + bltadat = do_get_mem_word((UWORD *)bltadatpt); bltadatpt -= 2; + } else + bltadat = blt_info.bltadat; + bltadat &= blit_masktable[i]; + blitahold = (((ULONG)bltadat << 16) | preva) >> blt_info.blitdownashift; + preva = bltadat; + if (bltbdatpt) { + UWORD bltbdat = do_get_mem_word((UWORD *)bltbdatpt); bltbdatpt -= 2; + blitbhold = (((ULONG)bltbdat << 16) | prevb) >> blt_info.blitdownbshift; + prevb = bltbdat; + } + if (bltcdatpt) { + blt_info.bltcdat = do_get_mem_word((UWORD *)bltcdatpt); bltcdatpt -= 2; + } + blt_info.bltddat = blit_func(blitahold, blitbhold, blt_info.bltcdat, mt) & 0xFFFF; if (blitfill) { UWORD d = blt_info.bltddat; int ifemode = blitife ? 2 : 0; @@ -179,16 +218,22 @@ static void blitter_dofast_desc(void) + (blit_filltable[d >> 8][ifemode + fc1][0] << 8)); blitfc = blit_filltable[d >> 8][ifemode + fc1][1]; } - blt_info.blitpreva = bltaold; blt_info.blitprevb = blt_info.bltbdat; if (blt_info.bltddat) blt_info.blitzero = 0; - if (bltddatpt) { *bltddatpt = blt_info.bltddat >> 8; *(bltddatpt + 1) = blt_info.bltddat; bltddatpt -= 2; } + if (bltddatpt) { + do_put_mem_word((UWORD *)bltddatpt, blt_info.bltddat); + bltddatpt -= 2; + } } if (bltadatpt) bltadatpt -= blt_info.bltamod; if (bltbdatpt) bltbdatpt -= blt_info.bltbmod; if (bltcdatpt) bltcdatpt -= blt_info.bltcmod; if (bltddatpt) bltddatpt -= blt_info.bltdmod; } + blt_info.bltbhold = blitbhold; } + blit_masktable[0] = 0xFFFF; + blit_masktable[blt_info.hblitsize - 1] = 0xFFFF; + bltstate = BLT_done; } @@ -196,10 +241,6 @@ static __inline__ int blitter_read(void) { if (bltcon0 & 0xe00){ if (!dmaen(DMA_BLITTER)) return 1; /* blitter stopped */ - if (!blitline){ - if (bltcon0 & 0x800) blt_info.bltadat = chipmem_bank.wget(bltapt); - if (bltcon0 & 0x400) blt_info.bltbdat = chipmem_bank.wget(bltbpt); - } if (bltcon0 & 0x200) blt_info.bltcdat = chipmem_bank.wget(bltcpt); } bltstate = BLT_work; @@ -217,97 +258,6 @@ static __inline__ int blitter_write(void return (bltcon0 & 0x100) != 0; } -static void blitter_blit(void) -{ - UWORD blitahold,blitbhold,blitchold; - UWORD bltaold; - - if (blitdesc) { - UWORD bltamask = 0xffff; - - if (!blitlpos) { bltamask &= blt_info.bltafwm; } - if (blitlpos == (blt_info.hblitsize - 1)) { bltamask &= blt_info.bltalwm; } - bltaold = blt_info.bltadat & bltamask; - - blitahold = (((ULONG)bltaold << 16) | blt_info.blitpreva) >> (16-blt_info.blitashift); - blitbhold = (((ULONG)blt_info.bltbdat << 16) | blt_info.blitprevb) >> (16-blt_info.blitbshift); - blitchold = blt_info.bltcdat; - } else { - UWORD bltamask = 0xffff; - - if (!blitlpos) { bltamask &= blt_info.bltafwm; } - if (blitlpos == (blt_info.hblitsize - 1)) { bltamask &= blt_info.bltalwm; } - bltaold = blt_info.bltadat & bltamask; - - blitahold = (((ULONG)blt_info.blitpreva << 16) | bltaold) >> blt_info.blitashift; - blitbhold = (((ULONG)blt_info.blitprevb << 16) | blt_info.bltbdat) >> blt_info.blitbshift; - blitchold = blt_info.bltcdat; - } - blt_info.bltddat = 0; - blt_info.bltddat = blit_func(blitahold, blitbhold, blitchold, bltcon0 & 0xFF); - if (blitfill){ - UWORD fillmask; - for (fillmask = 1; fillmask; fillmask <<= 1){ - UWORD tmp = blt_info.bltddat; - if (blitfc) { - if (blitife) - blt_info.bltddat |= fillmask; - else - blt_info.bltddat ^= fillmask; - } - if (tmp & fillmask) blitfc = !blitfc; - } - } - bltstate = BLT_write; - blt_info.blitpreva = bltaold; blt_info.blitprevb = blt_info.bltbdat; -} - -static void blitter_nxblit(void) -{ - bltstate = BLT_read; - if (blitdesc){ - if (++blitlpos == blt_info.hblitsize) { - if (--blt_info.vblitsize == 0) { - bltstate = BLT_done; -#if FAST_BLITTER == 0 - custom_bank.wput(0xDFF09C,0x8040); -#endif - } - blitfc = bltcon1 & 0x4; - - blitlpos = 0; - if (bltcon0 & 0x800) bltapt -= 2+blt_info.bltamod; - if (bltcon0 & 0x400) bltbpt -= 2+blt_info.bltbmod; - if (bltcon0 & 0x200) bltcpt -= 2+blt_info.bltcmod; - if (bltcon0 & 0x100) bltdpt -= 2+blt_info.bltdmod; - } else { - if (bltcon0 & 0x800) bltapt -= 2; - if (bltcon0 & 0x400) bltbpt -= 2; - if (bltcon0 & 0x200) bltcpt -= 2; - if (bltcon0 & 0x100) bltdpt -= 2; - } - } else { - if (++blitlpos == blt_info.hblitsize) { - if (--blt_info.vblitsize == 0) { - bltstate = BLT_done; -#if FAST_BLITTER == 0 - custom_bank.wput(0xDFF09C,0x8040); -#endif - } - blitlpos = 0; - if (bltcon0 & 0x800) bltapt += 2+blt_info.bltamod; - if (bltcon0 & 0x400) bltbpt += 2+blt_info.bltbmod; - if (bltcon0 & 0x200) bltcpt += 2+blt_info.bltcmod; - if (bltcon0 & 0x100) bltdpt += 2+blt_info.bltdmod; - } else { - if (bltcon0 & 0x800) bltapt += 2; - if (bltcon0 & 0x400) bltbpt += 2; - if (bltcon0 & 0x200) bltcpt += 2; - if (bltcon0 & 0x100) bltdpt += 2; - } - } -} - static __inline__ void blitter_line_incx(void) { if (++blinea_shift == 16) { @@ -386,9 +336,6 @@ static __inline__ void blitter_nxline(vo blineb = (blineb << 1) | (blineb >> 15); if (--blt_info.vblitsize == 0) { bltstate = BLT_done; -#if FAST_BLITTER == 0 - custom_bank.wput(0xDFF09C,0x8040); -#endif } else { bltstate = BLT_read; } @@ -397,9 +344,12 @@ static __inline__ void blitter_nxline(vo static void blit_init(void) { blitlpos = 0; - blt_info.blitzero = 1; blt_info.blitpreva = blt_info.blitprevb = 0; + blt_info.blitzero = 1; blitline = bltcon1 & 1; - blt_info.blitashift = bltcon0 >> 12; blt_info.blitbshift = bltcon1 >> 12; + blt_info.blitashift = bltcon0 >> 12; + blt_info.blitdownashift = 16 - blt_info.blitashift; + blt_info.blitbshift = bltcon1 >> 12; + blt_info.blitdownbshift = 16 - blt_info.blitbshift; if (blitline) { if (blt_info.hblitsize != 2) @@ -447,6 +397,7 @@ static void actually_do_blit(void) if (blitdesc) blitter_dofast_desc(); else blitter_dofast(); } + blitter_done_notify (); } void blitter_handler(void) @@ -466,48 +417,10 @@ void blitter_handler(void) void do_blitter(void) { -#if FAST_BLITTER == 0 - /* I'm not sure all this bltstate stuff is really necessary. - * Most programs should be OK if the blit is done as soon as BLTSIZE is - * written to, and the BLTFINISH bit is set some time after that. - * This code here is nowhere near exact. - */ - do { - switch(bltstate) { - case BLT_init: - blit_init(); - bltstate = BLT_read; - /* fall through */ - case BLT_read: - if (blitter_read()) - break; - /* fall through */ - case BLT_work: - if (blitline) - blitter_line(); - else - blitter_blit(); - /* fall through */ - case BLT_write: - if (blitter_write()) - break; - /* fall through */ - case BLT_next: - if (blitline) - blitter_nxline(); - else - blitter_nxblit(); - break; - case BLT_done: - regs.spcflags &= ~SPCFLAG_BLIT; - break; - } - } while(bltstate != BLT_done && dmaen(DMA_BLITTER) - && dmaen(DMA_BLITPRI)); /* blitter nasty -> no time for CPU */ -#else - { -#if FAST_BLITTER < 4 - long int blit_cycles = 2; + long int blit_cycles; + if (!immediate_blits) { + + blit_cycles = 2; if (!blitline) { if (bltcon0 & 0x400) @@ -516,21 +429,18 @@ void do_blitter(void) blit_cycles++; blit_cycles *= blt_info.vblitsize * blt_info.hblitsize; } -#else - long int blit_cycles = 1; -#endif - blit_init(); + } else + blit_cycles = 1; + + blit_init(); - eventtab[ev_blitter].active = 1; - eventtab[ev_blitter].oldcycles = cycles; - eventtab[ev_blitter].evtime = blit_cycles + cycles; - events_schedule(); + eventtab[ev_blitter].active = 1; + eventtab[ev_blitter].oldcycles = cycles; + eventtab[ev_blitter].evtime = blit_cycles + cycles; + events_schedule(); - regs.spcflags &= ~SPCFLAG_BLIT; - if (dmaen(DMA_BLITPRI)) - regs.spcflags |= SPCFLAG_BLTNASTY; - } -#endif + if (dmaen(DMA_BLITPRI)) + regs.spcflags |= SPCFLAG_BLTNASTY; } void maybe_blit(void)