--- uae/src/drawing.c 2018/04/24 16:42:10 1.1 +++ uae/src/drawing.c 2018/04/24 16:46:14 1.1.1.4 @@ -88,8 +88,8 @@ typedef void (*line_draw_func)(int, int) #define LINE_DECIDED 2 #define LINE_DECIDED_DOUBLE 3 #define LINE_AS_PREVIOUS 4 -#define LINE_BORDER_NEXT 5 -#define LINE_BORDER_PREV 6 +#define LINE_BLACK 5 +#define LINE_REMEMBERED_AS_BLACK 6 #define LINE_DONE 7 #define LINE_DONE_AS_PREVIOUS 8 #define LINE_REMEMBERED_AS_PREVIOUS 9 @@ -256,35 +256,38 @@ static void decode_ham_aga (int pix, int } #endif +static int linetoscr_double_offset; + #if AGA_CHIPSET != 0 /* WARNING: Not too much of this will work correctly yet. */ -static void pfield_linetoscr_aga(int pix, int stoppos) +static void pfield_linetoscr_aga (int pix, int lframe_end, int diw_end, int stoppos) { uae_u32 *buf = aga_lbufptr; int i; - int xor = (uae_u8)(bplcon4 >> 8); - int oldpix = pix; \ + int xor = (uae_u8)(dp_for_drawing->bplcon4 >> 8); + int oldpix = pix; - buf -= pix; \ + buf -= pix; for (i = 0; i < stoppos; i++) pixdata.apixels[i] ^= xor; - while (pix < dp_for_drawing->diwfirstword && pix < stoppos) { + while (pix < lframe_end) { buf[pix++] = colors_for_drawing.color_regs[0]; } if (bplham) { - while (pix < dp_for_drawing->diwlastword && pix < stoppos) { + while (pix < diw_end) { uae_u32 d = ham_linebuf[pix]; buf[pix] = d; pix++; } } else if (bpldualpf) { +#if 0 /* FIXME */ /* Dual playfield */ int *lookup = bpldualpfpri ? dblpf_aga2 : dblpf_aga1; int *lookup_no = bpldualpfpri ? dblpf_2nd2 : dblpf_2nd1; - while (pix < dp_for_drawing->diwlastword && pix < stoppos) { + while (pix < diw_end) { int pixcol = pixdata.apixels[pix]; int pfno = lookup_no[pixcol]; @@ -293,13 +296,14 @@ static void pfield_linetoscr_aga(int pix } else { int val = lookup[pixdata.apixels[pix]]; if (pfno == 2) - val += dblpfofs[(bplcon2 >> 10) & 7]; + val += dblpfofs[(dp_for_drawing->bplcon2 >> 10) & 7]; buf[pix] = colors_for_drawing.color_regs[val]; } pix++; } +#endif } else if (bplehb) { - while (pix < dp_for_drawing->diwlastword && pix < stoppos) { + while (pix < diw_end) { int pixcol = pixdata.apixels[pix]; uae_u32 d = colors_for_drawing.color_regs[pixcol]; /* What about sprites? */ @@ -309,7 +313,7 @@ static void pfield_linetoscr_aga(int pix pix++; } } else { - while (pix < dp_for_drawing->diwlastword && pix < stoppos) { + while (pix < diw_end) { int pixcol = pixdata.apixels[pix]; buf[pix] = colors_for_drawing.color_regs[pixcol]; pix++; @@ -321,12 +325,13 @@ static void pfield_linetoscr_aga(int pix aga_lbufptr += pix - oldpix; } -static void aga_translate32(int start, int stop) +static void aga_translate32 (int start, int stop) { - memcpy (((uae_u32 *)xlinebuffer) + start, aga_linebuf + start, 4*(stop-start)); + memcpy (((uae_u32 *)xlinebuffer) + start, aga_lbufptr, 4*(stop-start)); + aga_lbufptr += stop - start; } -static void aga_translate16(int start, int stop) +static void aga_translate16 (int start, int stop) { int i; for (i = start; i < stop; i++) { @@ -336,7 +341,7 @@ static void aga_translate16(int start, i } } -static void aga_translate8(int start, int stop) +static void aga_translate8 (int start, int stop) { int i; for (i = start; i < stop; i++) { @@ -345,9 +350,21 @@ static void aga_translate8(int start, in ((uae_u8 *)xlinebuffer)[i] = xcolors[v]; } } -#endif -static int linetoscr_double_offset; +static void aga_fill_line_32 (char *buf, int start, int stop) +{ + int i; + for (i = start; i < stop; i++) { + ((uae_u32 *)buf)[i] = colors_for_drawing.color_regs[0]; + } +} + +static void fill_line (void) +{ + aga_fill_line_32 (xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); +} + +#else /* no AGA_CHIPSET */ #define LINE_TO_SCR(NAME, TYPE, DO_DOUBLE, CONVERT) \ static void NAME(int pix, int lframe_end, int diw_end, int stoppos) \ @@ -405,7 +422,7 @@ static void NAME(int pix, int lframe_end } #define FILL_LINE(NAME, TYPE, CONVERT) \ -static void NAME(char *buf, int start, int stop) \ +static void NAME (char *buf, int start, int stop) \ { \ TYPE *b = (TYPE *)buf; \ int i;\ @@ -445,10 +462,10 @@ static void fill_line_24 (char *buf, int static __inline__ void fill_line_full (void) { switch (gfxvidinfo.pixbytes) { - case 1: fill_line_8(xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); break; - case 2: fill_line_16(xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); break; - case 3: fill_line_24(xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); break; - case 4: fill_line_32(xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); break; + case 1: fill_line_8 (xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); break; + case 2: fill_line_16 (xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); break; + case 3: fill_line_24 (xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); break; + case 4: fill_line_32 (xlinebuffer, linetoscr_x_adjust, linetoscr_x_adjust + gfxvidinfo.width); break; } } @@ -524,16 +541,16 @@ static __inline__ void fill_line (void) #undef pfield_linetoscr_full8 /* The types are lies, of course. */ -extern void pfield_linetoscr_normal_asm8(void) __asm__("pfield_linetoscr_normal_asm8"); -extern void pfield_linetoscr_ehb_asm8(void) __asm__("pfield_linetoscr_ehb_asm8"); -extern void pfield_linetoscr_ham6_asm8(void) __asm__("pfield_linetoscr_ham6_asm8"); -extern void pfield_linetoscr_dualpf_asm8(void) __asm__("pfield_linetoscr_dualpf_asm8"); -extern void pfield_linetoscr_hdouble_asm8(void) __asm__("pfield_linetoscr_hdouble_asm8"); -extern void pfield_linetoscr_hdouble_dpf_asm8(void) __asm__("pfield_linetoscr_hdouble_dpf_asm8"); -extern void pfield_linetoscr_hdouble_ehb_asm8(void) __asm__("pfield_linetoscr_hdouble_ehb_asm8"); -extern void pfield_linetoscr_asm8(void (*)(void), int, int, int, int, ...) __asm__("pfield_linetoscr_asm8"); +extern void pfield_linetoscr_normal_asm8 (void) __asm__("pfield_linetoscr_normal_asm8"); +extern void pfield_linetoscr_ehb_asm8 (void) __asm__("pfield_linetoscr_ehb_asm8"); +extern void pfield_linetoscr_ham6_asm8 (void) __asm__("pfield_linetoscr_ham6_asm8"); +extern void pfield_linetoscr_dualpf_asm8 (void) __asm__("pfield_linetoscr_dualpf_asm8"); +extern void pfield_linetoscr_hdouble_asm8 (void) __asm__("pfield_linetoscr_hdouble_asm8"); +extern void pfield_linetoscr_hdouble_dpf_asm8 (void) __asm__("pfield_linetoscr_hdouble_dpf_asm8"); +extern void pfield_linetoscr_hdouble_ehb_asm8 (void) __asm__("pfield_linetoscr_hdouble_ehb_asm8"); +extern void pfield_linetoscr_asm8 (void (*) (void), int, int, int, int, ...) __asm__("pfield_linetoscr_asm8"); -static void pfield_linetoscr_full8(int pix, int lframe_end, int diw_end, int stoppos) +static void pfield_linetoscr_full8 (int pix, int lframe_end, int diw_end, int stoppos) { int lframe_end_1, diw_end_1; @@ -541,30 +558,30 @@ static void pfield_linetoscr_full8(int p diw_end_1 = stoppos - ((stoppos - diw_end) & ~3); if (bplham && bplplanecnt == 6) { - pfield_linetoscr_asm8(pfield_linetoscr_ham6_asm8, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm8 (pfield_linetoscr_ham6_asm8, pix, lframe_end_1, diw_end_1, stoppos); } else if (bpldualpf) { #ifdef LORES_HACK if (currprefs.gfx_lores == 2) - pfield_linetoscr_asm8(pfield_linetoscr_hdouble_dpf_asm8, pix, lframe_end_1, diw_end_1, stoppos, + pfield_linetoscr_asm8 (pfield_linetoscr_hdouble_dpf_asm8, pix, lframe_end_1, diw_end_1, stoppos, bpldualpfpri ? dblpf_ind2 : dblpf_ind1); else #endif - pfield_linetoscr_asm8(pfield_linetoscr_dualpf_asm8, pix, lframe_end_1, diw_end_1, stoppos, + pfield_linetoscr_asm8 (pfield_linetoscr_dualpf_asm8, pix, lframe_end_1, diw_end_1, stoppos, bpldualpfpri ? dblpf_ind2 : dblpf_ind1); } else if (bplehb) { #ifdef LORES_HACK if (currprefs.gfx_lores == 2) - pfield_linetoscr_asm8(pfield_linetoscr_hdouble_ehb_asm8, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm8 (pfield_linetoscr_hdouble_ehb_asm8, pix, lframe_end_1, diw_end_1, stoppos); else #endif - pfield_linetoscr_asm8(pfield_linetoscr_ehb_asm8, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm8 (pfield_linetoscr_ehb_asm8, pix, lframe_end_1, diw_end_1, stoppos); } else { #ifdef LORES_HACK if (currprefs.gfx_lores == 2) - pfield_linetoscr_asm8(pfield_linetoscr_hdouble_asm8, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm8 (pfield_linetoscr_hdouble_asm8, pix, lframe_end_1, diw_end_1, stoppos); else #endif - pfield_linetoscr_asm8(pfield_linetoscr_normal_asm8, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm8 (pfield_linetoscr_normal_asm8, pix, lframe_end_1, diw_end_1, stoppos); } /* The assembly functions work on aligned data, so we may have to do some @@ -582,16 +599,16 @@ static void pfield_linetoscr_full8(int p } #undef pfield_linetoscr_full16 -extern void pfield_linetoscr_normal_asm16(void) __asm__("pfield_linetoscr_normal_asm16"); -extern void pfield_linetoscr_ehb_asm16(void) __asm__("pfield_linetoscr_ehb_asm16"); -extern void pfield_linetoscr_ham6_asm16(void) __asm__("pfield_linetoscr_ham6_asm16"); -extern void pfield_linetoscr_dualpf_asm16(void) __asm__("pfield_linetoscr_dualpf_asm16"); -extern void pfield_linetoscr_hdouble_asm16(void) __asm__("pfield_linetoscr_hdouble_asm16"); -extern void pfield_linetoscr_hdouble_dpf_asm16(void) __asm__("pfield_linetoscr_hdouble_dpf_asm16"); -extern void pfield_linetoscr_hdouble_ehb_asm16(void) __asm__("pfield_linetoscr_hdouble_ehb_asm16"); -extern void pfield_linetoscr_asm16(void (*)(void), int, int, int, int, ...) __asm__("pfield_linetoscr_asm16"); +extern void pfield_linetoscr_normal_asm16 (void) __asm__("pfield_linetoscr_normal_asm16"); +extern void pfield_linetoscr_ehb_asm16 (void) __asm__("pfield_linetoscr_ehb_asm16"); +extern void pfield_linetoscr_ham6_asm16 (void) __asm__("pfield_linetoscr_ham6_asm16"); +extern void pfield_linetoscr_dualpf_asm16 (void) __asm__("pfield_linetoscr_dualpf_asm16"); +extern void pfield_linetoscr_hdouble_asm16 (void) __asm__("pfield_linetoscr_hdouble_asm16"); +extern void pfield_linetoscr_hdouble_dpf_asm16 (void) __asm__("pfield_linetoscr_hdouble_dpf_asm16"); +extern void pfield_linetoscr_hdouble_ehb_asm16 (void) __asm__("pfield_linetoscr_hdouble_ehb_asm16"); +extern void pfield_linetoscr_asm16 (void (*) (void), int, int, int, int, ...) __asm__("pfield_linetoscr_asm16"); -static void pfield_linetoscr_full16(int pix, int lframe_end, int diw_end, int stoppos) +static void pfield_linetoscr_full16 (int pix, int lframe_end, int diw_end, int stoppos) { int lframe_end_1, diw_end_1; @@ -599,30 +616,30 @@ static void pfield_linetoscr_full16(int diw_end_1 = stoppos - ((stoppos - diw_end) & ~3); if (bplham && bplplanecnt == 6) { - pfield_linetoscr_asm16(pfield_linetoscr_ham6_asm16, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm16 (pfield_linetoscr_ham6_asm16, pix, lframe_end_1, diw_end_1, stoppos); } else if (bpldualpf) { #ifdef LORES_HACK if (currprefs.gfx_lores == 2) - pfield_linetoscr_asm16(pfield_linetoscr_hdouble_dpf_asm16, pix, lframe_end_1, diw_end_1, stoppos, + pfield_linetoscr_asm16 (pfield_linetoscr_hdouble_dpf_asm16, pix, lframe_end_1, diw_end_1, stoppos, bpldualpfpri ? dblpf_ind2 : dblpf_ind1); else #endif - pfield_linetoscr_asm16(pfield_linetoscr_dualpf_asm16, pix, lframe_end_1, diw_end_1, stoppos, + pfield_linetoscr_asm16 (pfield_linetoscr_dualpf_asm16, pix, lframe_end_1, diw_end_1, stoppos, bpldualpfpri ? dblpf_ind2 : dblpf_ind1); } else if (bplehb) { #ifdef LORES_HACK if (currprefs.gfx_lores == 2) - pfield_linetoscr_asm16(pfield_linetoscr_hdouble_ehb_asm16, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm16 (pfield_linetoscr_hdouble_ehb_asm16, pix, lframe_end_1, diw_end_1, stoppos); else #endif - pfield_linetoscr_asm16(pfield_linetoscr_ehb_asm16, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm16 (pfield_linetoscr_ehb_asm16, pix, lframe_end_1, diw_end_1, stoppos); } else { #ifdef LORES_HACK if (currprefs.gfx_lores == 2) - pfield_linetoscr_asm16(pfield_linetoscr_hdouble_asm16, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm16 (pfield_linetoscr_hdouble_asm16, pix, lframe_end_1, diw_end_1, stoppos); else #endif - pfield_linetoscr_asm16(pfield_linetoscr_normal_asm16, pix, lframe_end_1, diw_end_1, stoppos); + pfield_linetoscr_asm16 (pfield_linetoscr_normal_asm16, pix, lframe_end_1, diw_end_1, stoppos); } /* The assembly functions work on aligned data, so we may have to do some @@ -649,22 +666,24 @@ static void pfield_linetoscr_full16(int #ifdef NO_DOUBLING_LINETOSCR #undef pfield_linetoscr_full8_double #undef pfield_linetoscr_full16_double -static void pfield_linetoscr_full8_double(int start, int lframe_end, int diw_end, int stop) +static void pfield_linetoscr_full8_double (int start, int lframe_end, int diw_end, int stop) { char *oldxlb = (char *)xlinebuffer; - pfield_linetoscr_full8(start, lframe_end, diw_end, stop); + pfield_linetoscr_full8 (start, lframe_end, diw_end, stop); xlinebuffer = oldxlb + linetoscr_double_offset; - pfield_linetoscr_full8(start, lframe_end, diw_end, stop); + pfield_linetoscr_full8 (start, lframe_end, diw_end, stop); } -static void pfield_linetoscr_full16_double(int start, int lframe_end, int diw_end, int stop) +static void pfield_linetoscr_full16_double (int start, int lframe_end, int diw_end, int stop) { char *oldxlb = (char *)xlinebuffer; - pfield_linetoscr_full16(start, lframe_end, diw_end, stop); + pfield_linetoscr_full16 (start, lframe_end, diw_end, stop); xlinebuffer = oldxlb + linetoscr_double_offset; - pfield_linetoscr_full16(start, lframe_end, diw_end, stop); + pfield_linetoscr_full16 (start, lframe_end, diw_end, stop); } #endif +#endif /* no AGA_CHIPSET */ + static int linetoscr_diw_end, linetoscr_diw_start; /* Initialize the variables necessary for drawing a line. @@ -688,8 +707,10 @@ static void pfield_init_linetoscr (void) * with sprites. */ if (dip_for_drawing->nr_sprites == 0) { int hiresadjust = bplhires ? 4 : 8; - ddf_left = ((dp_for_drawing->plfstrt + hiresadjust)*2 + mindelay - DISPLAY_LEFT_SHIFT) << lores_shift; - ddf_right = ((dp_for_drawing->plfstrt + dp_for_drawing->plflinelen + hiresadjust)*2 + maxdelay - DISPLAY_LEFT_SHIFT) << lores_shift; + ddf_left = (((dp_for_drawing->plfstrt + hiresadjust)*2 + + mindelay - DISPLAY_LEFT_SHIFT) << lores_shift); + ddf_right = (((dp_for_drawing->plfstrt + dp_for_drawing->plflinelen + hiresadjust)*2 + + maxdelay - DISPLAY_LEFT_SHIFT) << lores_shift); if (linetoscr_diw_start < ddf_left) linetoscr_diw_start = ddf_left; @@ -780,11 +801,11 @@ static void pfield_do_linetoscr(int star } } #else - pfield_linetoscr_aga(start, lframe_end, diw_end, stop); + pfield_linetoscr_aga (start, lframe_end, diw_end, stop); #endif } -static void pfield_do_fill_line(int start, int stop) +static void pfield_do_fill_line (int start, int stop) { if (stop > linetoscr_right_x) stop = linetoscr_right_x; @@ -794,15 +815,20 @@ static void pfield_do_fill_line(int star if (start >= stop) return; +#if AGA_CHIPSET == 0 switch (gfxvidinfo.pixbytes) { case 1: fill_line_8 (xlinebuffer, start, stop); break; case 2: fill_line_16 (xlinebuffer, start, stop); break; case 3: fill_line_24 (xlinebuffer, start, stop); break; case 4: fill_line_32 (xlinebuffer, start, stop); break; } +#else + aga_fill_line_32 (xlinebuffer, start, stop); + /* FIXME */ +#endif } -static void pfield_do_linetoscr_full(int double_line) +static void pfield_do_linetoscr_full (int double_line) { int start = linetoscr_x_adjust, stop = start + gfxvidinfo.width; int lframe_end = linetoscr_diw_start, diw_end = linetoscr_diw_end; @@ -827,11 +853,11 @@ static void pfield_do_linetoscr_full(int case 4: pfield_linetoscr_full32 (start, lframe_end, diw_end, stop); break; } #else - pfield_linetoscr_aga(start, lframe_end, diw_end, stop); + pfield_linetoscr_aga (start, lframe_end, diw_end, stop); #endif } -static void gen_pfield_tables(void) +static void gen_pfield_tables (void) { int i; union { @@ -1768,11 +1794,20 @@ static __inline__ void do_flush_screen ( flush_screen (start, stop); } +static __inline__ void finish_line_aga (void) +{ +#if AGA_CHIPSET != 0 + aga_lbufptr = aga_linebuf; + aga_translate32 (linetoscr_x_adjust_bytes, linetoscr_x_adjust_bytes + gfxvidinfo.width); +#endif +} + static int drawing_color_matches; static enum { color_match_acolors, color_match_full } color_match_type; static void adjust_drawing_colors (int ctable, int bplham) { +#if AGA_CHIPSET == 0 if (drawing_color_matches != ctable) { if (bplham) { memcpy (&colors_for_drawing, curr_color_tables + ctable, @@ -1789,6 +1824,13 @@ static void adjust_drawing_colors (int c sizeof colors_for_drawing.color_regs); color_match_type = color_match_full; } +#else + if (drawing_color_matches != ctable) { + memcpy (&colors_for_drawing, curr_color_tables + ctable, + sizeof colors_for_drawing); + drawing_color_matches = ctable; + } +#endif } static __inline__ void adjust_color0_for_color_change (void) @@ -1796,7 +1838,9 @@ static __inline__ void adjust_color0_for drawing_color_matches = -1; if (dp_for_drawing->color0 != 0xFFFFFFFFul) { colors_for_drawing.color_regs[0] = dp_for_drawing->color0; +#if AGA_CHIPSET == 0 colors_for_drawing.acolors[0] = xcolors[dp_for_drawing->color0]; +#endif } } @@ -1818,7 +1862,9 @@ static __inline__ void do_color_changes worker (lastpos, nextpos); if (i != dip_for_drawing->last_color_change) { colors_for_drawing.color_regs[cc->regno] = cc->value; +#if AGA_CHIPSET == 0 colors_for_drawing.acolors[cc->regno] = xcolors[cc->value]; +#endif } if (nextpos > lastpos) { lastpos = nextpos; @@ -1834,7 +1880,7 @@ static __inline__ void do_color_changes static void pfield_expand_dp_bplcon (void) { bplhires = (dp_for_drawing->bplcon0 & 0x8000) == 0x8000; - bplplanecnt = (dp_for_drawing->bplcon0 & 0x7000) >> 12; + bplplanecnt = GET_PLANES (dp_for_drawing->bplcon0); bplham = (dp_for_drawing->bplcon0 & 0x800) == 0x800; #if AGA_CHIPSET == 1 /* The KILLEHB bit exists in ECS, but is apparently meant for Genlock * stuff, and it's set by some demos (e.g. Andromeda Seven Seas) */ @@ -1862,10 +1908,9 @@ static __inline__ void pfield_draw_line int do_double = 0; enum double_how dh; - dp_for_drawing = 0; - dip_for_drawing = 0; + dp_for_drawing = line_decisions + lineno; + dip_for_drawing = curr_drawinfo + lineno; switch (linestate[lineno]) { - case LINE_AS_PREVIOUS: case LINE_REMEMBERED_AS_PREVIOUS: { static int warned = 0; @@ -1875,16 +1920,22 @@ static __inline__ void pfield_draw_line line_decisions[lineno].which = -2; return; - case LINE_BORDER_PREV: - border = 1; - dp_for_drawing = line_decisions + lineno - 1; - dip_for_drawing = curr_drawinfo + lineno - 1; + case LINE_BLACK: + line_decisions[lineno].which = -2; + linestate[lineno] = LINE_REMEMBERED_AS_BLACK; + border = 2; break; - case LINE_BORDER_NEXT: - border = 1; - dp_for_drawing = line_decisions + lineno + 1; - dip_for_drawing = curr_drawinfo + lineno + 1; + case LINE_REMEMBERED_AS_BLACK: + return; + + case LINE_AS_PREVIOUS: + dp_for_drawing--; + dip_for_drawing--; + if (dp_for_drawing->which != 1) + border = 1; + line_decisions[lineno].which = -2; + linestate[lineno] = LINE_DONE_AS_PREVIOUS; break; case LINE_DONE_AS_PREVIOUS: @@ -1898,45 +1949,27 @@ static __inline__ void pfield_draw_line if (follow_ypos != -1) { do_double = 1; linetoscr_double_offset = gfxvidinfo.rowbytes * (follow_ypos - gfx_ypos); + linestate[lineno + 1] = LINE_DONE_AS_PREVIOUS; } /* fall through */ default: - dip_for_drawing = curr_drawinfo + lineno; - dp_for_drawing = line_decisions + lineno; if (dp_for_drawing->which != 1) border = 1; - break; - } - - if (!line_changed[lineno] && !frame_redraw_necessary) { - /* The case where we can skip redrawing this line. If this line - * is supposed to be doubled, and the next line is remembered as - * having been doubled, then the next line is done as well. */ - if (do_double) { - /* @@@ This is buggy. FIXME */ - if (linestate[lineno+1] != LINE_REMEMBERED_AS_PREVIOUS) { - if (gfxvidinfo.linemem == 0) - memcpy (row_map[follow_ypos], row_map[gfx_ypos], gfxvidinfo.rowbytes); - line_decisions[lineno + 1].which = -2; - do_flush_line (follow_ypos); - } - linestate[lineno + 1] = LINE_DONE_AS_PREVIOUS; - } linestate[lineno] = LINE_DONE; - return; + break; } dh = dh_line; xlinebuffer = gfxvidinfo.linemem; - if (xlinebuffer == 0 && do_double && dip_for_drawing->nr_color_changes != 0) + if (xlinebuffer == 0 && do_double && border != 2 && dip_for_drawing->nr_color_changes != 0) xlinebuffer = gfxvidinfo.emergmem, dh = dh_emerg; if (xlinebuffer == 0) xlinebuffer = row_map[gfx_ypos], dh = dh_buf; xlinebuffer -= linetoscr_x_adjust_bytes; aga_lbufptr = aga_linebuf; - if (!border) { + if (border == 0) { pfield_expand_dp_bplcon (); #ifdef LORES_HACK @@ -1983,8 +2016,8 @@ static __inline__ void pfield_draw_line if (dip_for_drawing->nr_color_changes == 0) { pfield_do_linetoscr_full (dh == dh_buf ? do_double : 0); + finish_line_aga (); do_flush_line (gfx_ypos); - linestate[lineno] = LINE_DONE; #if 0 if (dh == dh_emerg) abort (); @@ -1993,24 +2026,22 @@ static __inline__ void pfield_draw_line /* If dh == dh_line, do_flush_line will re-use the rendered line * from linemem. If dh == dh_buf, the line will have been doubled * by pfield_do_linetoscr_full. */ - linestate[lineno + 1] = LINE_DONE_AS_PREVIOUS; do_flush_line (follow_ypos); } } else { adjust_color0_for_color_change (); do_color_changes (pfield_do_linetoscr); + finish_line_aga (); if (dh == dh_emerg) memcpy (row_map[gfx_ypos], xlinebuffer + linetoscr_x_adjust_bytes, gfxvidinfo.rowbytes); - linestate[lineno] = LINE_DONE; do_flush_line (gfx_ypos); if (do_double) { if (dh == dh_emerg) memcpy (row_map[follow_ypos], xlinebuffer + linetoscr_x_adjust_bytes, gfxvidinfo.rowbytes); else if (dh == dh_buf) memcpy (row_map[follow_ypos], row_map[gfx_ypos], gfxvidinfo.rowbytes); - linestate[lineno + 1] = LINE_DONE_AS_PREVIOUS; line_decisions[lineno + 1].which = -2; do_flush_line (follow_ypos); } @@ -2019,7 +2050,7 @@ static __inline__ void pfield_draw_line if (currprefs.gfx_lores == 2) currprefs.gfx_lores = 0; #endif - } else { /* Border. */ + } else if (border == 1) { adjust_drawing_colors (dp_for_drawing->ctable, 0); /* Check color0 adjust only if we have color changes - shouldn't happen @@ -2028,7 +2059,6 @@ static __inline__ void pfield_draw_line if (dip_for_drawing->nr_color_changes == 0) { fill_line (); do_flush_line (gfx_ypos); - linestate[lineno] = LINE_DONE; #if 0 if (dh == dh_emerg) abort (); @@ -2041,7 +2071,6 @@ static __inline__ void pfield_draw_line /* If dh == dh_line, do_flush_line will re-use the rendered line * from linemem. */ do_flush_line (follow_ypos); - linestate[lineno+1] = LINE_DONE_AS_PREVIOUS; } return; } @@ -2053,7 +2082,6 @@ static __inline__ void pfield_draw_line memcpy (row_map[gfx_ypos], xlinebuffer + linetoscr_x_adjust_bytes, gfxvidinfo.rowbytes); do_flush_line (gfx_ypos); - linestate[lineno] = LINE_DONE; if (do_double) { if (dh == dh_emerg) memcpy (row_map[follow_ypos], xlinebuffer + linetoscr_x_adjust_bytes, gfxvidinfo.rowbytes); @@ -2062,9 +2090,16 @@ static __inline__ void pfield_draw_line /* If dh == dh_line, do_flush_line will re-use the rendered line * from linemem. */ do_flush_line (follow_ypos); - linestate[lineno + 1] = LINE_DONE_AS_PREVIOUS; line_decisions[lineno + 1].which = -2; } + } else { +#if AGA_CHIPSET == 0 + xcolnr tmp = colors_for_drawing.acolors[0]; + colors_for_drawing.acolors[0] = xcolors[0]; + fill_line (); + do_flush_line (gfx_ypos); + colors_for_drawing.acolors[0] = tmp; +#endif } } @@ -2233,8 +2268,18 @@ static void init_drawing_frame (void) maxline = currprefs.gfx_linedbl ? (maxvpos+1) * 2 + 1 : (maxvpos+1) + 1; #ifdef SMART_UPDATE - for (i = 0; i < maxline; i++) - linestate[i] = linestate[i] == LINE_DONE_AS_PREVIOUS ? LINE_REMEMBERED_AS_PREVIOUS : LINE_UNDECIDED; + for (i = 0; i < maxline; i++) { + switch (linestate[i]) { + case LINE_DONE_AS_PREVIOUS: + linestate[i] = LINE_REMEMBERED_AS_PREVIOUS; + break; + case LINE_REMEMBERED_AS_BLACK: + break; + default: + linestate[i] = LINE_UNDECIDED; + break; + } + } #else memset (linestate, LINE_UNDECIDED, maxline); #endif @@ -2338,9 +2383,9 @@ static __inline__ void check_picasso (vo picasso_on = picasso_requested_on; if (!picasso_on) - clear_inhibit_frame (2); + clear_inhibit_frame (IHF_PICASSO); else - set_inhibit_frame (2); + set_inhibit_frame (IHF_PICASSO); gfx_set_picasso_state (picasso_on); picasso_enablescreen (picasso_requested_on); @@ -2368,7 +2413,7 @@ void vsync_handle_redraw (int long_frame if (quit_program < 0) { quit_program = -quit_program; - set_inhibit_frame (1); + set_inhibit_frame (IHF_QUIT_PROGRAM); regs.spcflags |= SPCFLAG_BRK; filesys_prepare_reset (); #ifdef SUPPORT_PENGUINS @@ -2382,6 +2427,7 @@ void vsync_handle_redraw (int long_frame count_frame (); check_picasso (); + check_prefs_changed_audio (); check_prefs_changed_custom (); check_prefs_changed_cpu (); if (check_prefs_changed_gfx ()) { @@ -2399,30 +2445,40 @@ void vsync_handle_redraw (int long_frame } } -void hsync_record_line_state (int lineno, enum nln_how how) +void hsync_record_line_state (int lineno, enum nln_how how, int changed) { + char *state; if (framecnt != 0) return; + + state = linestate + lineno; + changed += frame_redraw_necessary; + switch (how) { case nln_normal: - linestate[lineno] = LINE_DECIDED; + *state = changed ? LINE_DECIDED : LINE_DONE; break; case nln_doubled: - linestate[lineno] = LINE_DECIDED_DOUBLE; - if (linestate[lineno+1] != LINE_REMEMBERED_AS_PREVIOUS) - linestate[lineno+1] = LINE_AS_PREVIOUS; + *state = changed ? LINE_DECIDED_DOUBLE : LINE_DONE; + changed += state[1] != LINE_REMEMBERED_AS_PREVIOUS; + state[1] = changed ? LINE_AS_PREVIOUS : LINE_DONE_AS_PREVIOUS; + break; + case nln_nblack: + *state = changed ? LINE_DECIDED : LINE_DONE; + if (state[1] != LINE_REMEMBERED_AS_BLACK) + state[1] = LINE_BLACK; break; case nln_lower: - if (linestate[lineno-1] == LINE_UNDECIDED) - linestate[lineno-1] = LINE_BORDER_NEXT; - linestate[lineno] = LINE_DECIDED; + if (state[-1] == LINE_UNDECIDED) + state[-1] = LINE_BLACK; + *state = changed ? LINE_DECIDED : LINE_DONE; break; case nln_upper: - linestate[lineno] = LINE_DECIDED; - if (linestate[lineno+1] == LINE_UNDECIDED - || linestate[lineno+1] == LINE_REMEMBERED_AS_PREVIOUS - || linestate[lineno+1] == LINE_AS_PREVIOUS) - linestate[lineno+1] = LINE_BORDER_PREV; + *state = changed ? LINE_DECIDED : LINE_DONE; + if (state[1] == LINE_UNDECIDED + || state[1] == LINE_REMEMBERED_AS_PREVIOUS + || state[1] == LINE_AS_PREVIOUS) + state[1] = LINE_BLACK; break; } }