diff options
| author | rin <rin@NetBSD.org> | 2019-07-29 02:57:41 +0000 |
|---|---|---|
| committer | rin <rin@NetBSD.org> | 2019-07-29 02:57:41 +0000 |
| commit | 86fd2c7ec1aba29f20cd1c4be24fa4bb24ae9fa0 (patch) | |
| tree | 37964f270d73f7a7fba5250953f1ee58ee3100c4 /sys/dev/rasops | |
| parent | 7a6e3f20ca77cdb50f83d305c2d92c7e14d1ddd4 (diff) | |
Clean up for rasops1.c:
- dedup ugly copy-paste
- rewrite to factorize width-optimized putchar functions
- misc style
Diffstat (limited to 'sys/dev/rasops')
| -rw-r--r-- | sys/dev/rasops/rasops1.c | 336 | ||||
| -rw-r--r-- | sys/dev/rasops/rasops1_putchar_width.h | 137 |
2 files changed, 212 insertions, 261 deletions
diff --git a/sys/dev/rasops/rasops1.c b/sys/dev/rasops/rasops1.c index 2af5f459fe6..cc20a4f7649 100644 --- a/sys/dev/rasops/rasops1.c +++ b/sys/dev/rasops/rasops1.c @@ -1,4 +1,4 @@ -/* $NetBSD: rasops1.c,v 1.28 2019/07/25 03:02:44 rin Exp $ */ +/* $NetBSD: rasops1.c,v 1.29 2019/07/29 02:57:41 rin Exp $ */ /*- * Copyright (c) 1999 The NetBSD Foundation, Inc. @@ -30,7 +30,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: rasops1.c,v 1.28 2019/07/25 03:02:44 rin Exp $"); +__KERNEL_RCSID(0, "$NetBSD: rasops1.c,v 1.29 2019/07/29 02:57:41 rin Exp $"); #include "opt_rasops.h" @@ -60,6 +60,12 @@ void rasops1_init(struct rasops_info *ri) { + if ((ri->ri_font->fontwidth & 7) != 0) { + ri->ri_ops.erasecols = rasops1_erasecols; + ri->ri_ops.copycols = rasops1_copycols; + ri->ri_do_cursor = rasops1_do_cursor; + } + switch (ri->ri_font->fontwidth) { #ifndef RASOPS_SMALL case 8: @@ -73,12 +79,6 @@ rasops1_init(struct rasops_info *ri) ri->ri_ops.putchar = rasops1_putchar; break; } - - if ((ri->ri_font->fontwidth & 7) != 0) { - ri->ri_ops.erasecols = rasops1_erasecols; - ri->ri_ops.copycols = rasops1_copycols; - ri->ri_do_cursor = rasops1_do_cursor; - } } /* @@ -87,12 +87,15 @@ rasops1_init(struct rasops_info *ri) static void rasops1_putchar(void *cookie, int row, int col, u_int uc, long attr) { - u_int fs, rs, fb, bg, fg, lmask, rmask; - uint32_t height, width; struct rasops_info *ri = (struct rasops_info *)cookie; struct wsdisplay_font *font = PICK_FONT(ri, uc); - uint32_t *rp, *hrp = NULL, tmp, tmp2; + uint32_t fs, rs, fb, bg, fg, lmask, rmask; + uint32_t height, width; + uint32_t *rp, *hrp, tmp, tmp0, tmp1; uint8_t *fr; + bool space; + + hrp = NULL; /* XXX GCC */ #ifdef RASOPS_CLIPPING /* Catches 'row < 0' case too */ @@ -111,30 +114,31 @@ rasops1_putchar(void *cookie, int row, int col, u_int uc, long attr) ((col >> 3) & ~3)); height = font->fontheight; width = font->fontwidth; - col = col & 31; + col &= 31; rs = ri->ri_stride; bg = (attr & 0x000f0000) ? ri->ri_devcmap[1] : ri->ri_devcmap[0]; fg = (attr & 0x0f000000) ? ri->ri_devcmap[1] : ri->ri_devcmap[0]; /* If fg and bg match this becomes a space character */ - if (fg == bg || uc == ' ') { - uc = (u_int)-1; - fr = 0; /* shutup gcc */ - fs = 0; /* shutup gcc */ + if (uc == ' ' || fg == bg) { + space = true; + fr = NULL; /* XXX GCC */ + fs = 0; /* XXX GCC */ } else { + space = false; fr = FONT_GLYPH(uc, font, ri); fs = font->stride; } - /* Single word, one mask */ - if ((col + width) <= 32) { + if (col + width <= 32) { + /* Single word, only one mask */ + rmask = rasops_pmask[col][width]; lmask = ~rmask; - if (uc == (u_int)-1) { + if (space) { bg &= rmask; - while (height--) { tmp = (*rp & lmask) | bg; *rp = tmp; @@ -145,36 +149,19 @@ rasops1_putchar(void *cookie, int row, int col, u_int uc, long attr) } } } else { - /* NOT fontbits if bg is white */ - if (bg) { - while (height--) { - fb = ~(fr[3] | (fr[2] << 8) | - (fr[1] << 16) | (fr[0] << 24)); - tmp = (*rp & lmask) - | (MBE(fb >> col) & rmask); - *rp = tmp; - - fr += fs; - DELTA(rp, rs, uint32_t *); - if (ri->ri_hwbits) { - *hrp = tmp; - DELTA(hrp, rs, uint32_t *); - } - } - } else { - while (height--) { - fb = (fr[3] | (fr[2] << 8) | - (fr[1] << 16) | (fr[0] << 24)); - tmp = (*rp & lmask) - | (MBE(fb >> col) & rmask); - *rp = tmp; - - fr += fs; - DELTA(rp, rs, uint32_t *); - if (ri->ri_hwbits) { - *hrp = tmp; - DELTA(hrp, rs, uint32_t *); - } + while (height--) { + tmp = *rp & lmask; + fb = fr[3] | (fr[2] << 8) | + (fr[1] << 16) | (fr[0] << 24); + fr += fs; + if (bg) + fb = ~fb; + tmp |= (MBE(fb >> col) & rmask); + *rp = tmp; + DELTA(rp, rs, uint32_t *); + if (ri->ri_hwbits) { + *hrp = tmp; + DELTA(hrp, rs, uint32_t *); } } } @@ -190,68 +177,45 @@ rasops1_putchar(void *cookie, int row, int col, u_int uc, long attr) } } } else { + /* Word boundary, two masks needed */ + lmask = ~rasops_lmask[col]; rmask = ~rasops_rmask[(col + width) & 31]; - if (uc == (u_int)-1) { + if (space) { width = bg & ~rmask; bg = bg & ~lmask; - while (height--) { - tmp = (rp[0] & lmask) | bg; - tmp2 = (rp[1] & rmask) | width; - rp[0] = tmp; - rp[1] = tmp2; + tmp0 = (rp[0] & lmask) | bg; + tmp1 = (rp[1] & rmask) | width; + rp[0] = tmp0; + rp[1] = tmp1; DELTA(rp, rs, uint32_t *); if (ri->ri_hwbits) { - hrp[0] = tmp; - hrp[1] = tmp2; + hrp[0] = tmp0; + hrp[1] = tmp1; DELTA(hrp, rs, uint32_t *); } } } else { width = 32 - col; - - /* NOT fontbits if bg is white */ - if (bg) { - while (height--) { - fb = ~(fr[3] | (fr[2] << 8) | - (fr[1] << 16) | (fr[0] << 24)); - - tmp = (rp[0] & lmask) | - MBE((u_int)fb >> col); - - tmp2 = (rp[1] & rmask) | - (MBE((u_int)fb << width) & ~rmask); - rp[0] = tmp; - rp[1] = tmp2; - fr += fs; - DELTA(rp, rs, uint32_t *); - if (ri->ri_hwbits) { - hrp[0] = tmp; - hrp[1] = tmp2; - DELTA(hrp, rs, uint32_t *); - } - } - } else { - while (height--) { - fb = (fr[3] | (fr[2] << 8) | - (fr[1] << 16) | (fr[0] << 24)); - - tmp = (rp[0] & lmask) | - MBE(fb >> col); - - tmp2 = (rp[1] & rmask) | - (MBE(fb << width) & ~rmask); - rp[0] = tmp; - rp[1] = tmp2; - fr += fs; - DELTA(rp, rs, uint32_t *); - if (ri->ri_hwbits) { - hrp[0] = tmp; - hrp[1] = tmp2; - DELTA(hrp, rs, uint32_t *); - } + while (height--) { + tmp0 = rp[0] & lmask; + tmp1 = rp[1] & rmask; + fb = fr[3] | (fr[2] << 8) | + (fr[1] << 16) | (fr[0] << 24); + fr += fs; + if (bg) + fb = ~fb; + tmp0 |= MBE(fb >> col); + tmp1 |= (MBE(fb << width) & ~rmask); + rp[0] = tmp0; + rp[1] = tmp1; + DELTA(rp, rs, uint32_t *); + if (ri->ri_hwbits) { + hrp[0] = tmp0; + hrp[1] = tmp1; + DELTA(hrp, rs, uint32_t *); } } } @@ -259,179 +223,29 @@ rasops1_putchar(void *cookie, int row, int col, u_int uc, long attr) /* Do underline */ if ((attr & WSATTR_UNDERLINE) != 0) { DELTA(rp, -(ri->ri_stride << 1), uint32_t *); - tmp = (rp[0] & lmask) | (fg & ~lmask); - tmp2 = (rp[1] & rmask) | (fg & ~rmask); - rp[0] = tmp; - rp[1] = tmp2; + tmp0 = (rp[0] & lmask) | (fg & ~lmask); + tmp1 = (rp[1] & rmask) | (fg & ~rmask); + rp[0] = tmp0; + rp[1] = tmp1; if (ri->ri_hwbits) { DELTA(hrp, -(ri->ri_stride << 1), uint32_t *); - hrp[0] = tmp; - hrp[1] = tmp2; + hrp[0] = tmp0; + hrp[1] = tmp1; } } } } #ifndef RASOPS_SMALL -/* - * Paint a single character. This is for 8-pixel wide fonts. - */ -static void -rasops1_putchar8(void *cookie, int row, int col, u_int uc, long attr) -{ - int height, fs, rs, bg, fg; - struct rasops_info *ri = (struct rasops_info *)cookie; - struct wsdisplay_font *font = PICK_FONT(ri, uc); - uint8_t *fr, *rp, *hrp = NULL; - -#ifdef RASOPS_CLIPPING - /* Catches 'row < 0' case too */ - if ((unsigned)row >= (unsigned)ri->ri_rows) - return; - if ((unsigned)col >= (unsigned)ri->ri_cols) - return; -#endif +#define RASOPS_WIDTH 8 +#include "rasops1_putchar_width.h" +#undef RASOPS_WIDTH - rp = ri->ri_bits + row * ri->ri_yscale + col * ri->ri_xscale; - if (ri->ri_hwbits) - hrp = ri->ri_hwbits + row * ri->ri_yscale + col * ri->ri_xscale; - height = font->fontheight; - rs = ri->ri_stride; - - bg = (attr & 0x000f0000) ? ri->ri_devcmap[1] : ri->ri_devcmap[0]; - fg = (attr & 0x0f000000) ? ri->ri_devcmap[1] : ri->ri_devcmap[0]; - - /* If fg and bg match this becomes a space character */ - if (fg == bg || uc == ' ') { - while (height--) { - *rp = bg; - rp += rs; - if (ri->ri_hwbits) { - *hrp = bg; - hrp += rs; - } - } - } else { - fr = FONT_GLYPH(uc, font, ri); - fs = font->stride; +#define RASOPS_WIDTH 16 +#include "rasops1_putchar_width.h" +#undef RASOPS_WIDTH - /* NOT fontbits if bg is white */ - if (bg) { - while (height--) { - *rp = ~*fr; - rp += rs; - if (ri->ri_hwbits) { - *hrp = ~*fr; - hrp += rs; - } - fr += fs; - - } - } else { - while (height--) { - *rp = *fr; - rp += rs; - if (ri->ri_hwbits) { - *hrp = *fr; - hrp += rs; - } - fr += fs; - } - } - - } - - /* Do underline */ - if ((attr & WSATTR_UNDERLINE) != 0) { - rp[-(ri->ri_stride << 1)] = fg; - if (ri->ri_hwbits) { - hrp[-(ri->ri_stride << 1)] = fg; - } - } -} - -/* - * Paint a single character. This is for 16-pixel wide fonts. - */ -static void -rasops1_putchar16(void *cookie, int row, int col, u_int uc, long attr) -{ - int height, fs, rs, bg, fg; - struct rasops_info *ri = (struct rasops_info *)cookie; - struct wsdisplay_font *font = PICK_FONT(ri, uc); - uint8_t *fr, *rp, *hrp = NULL; - -#ifdef RASOPS_CLIPPING - /* Catches 'row < 0' case too */ - if ((unsigned)row >= (unsigned)ri->ri_rows) - return; - - if ((unsigned)col >= (unsigned)ri->ri_cols) - return; -#endif - - rp = ri->ri_bits + row * ri->ri_yscale + col * ri->ri_xscale; - if (ri->ri_hwbits) - hrp = ri->ri_hwbits + row * ri->ri_yscale + col * ri->ri_xscale; - height = font->fontheight; - rs = ri->ri_stride; - - bg = (attr & 0x000f0000) ? ri->ri_devcmap[1] : ri->ri_devcmap[0]; - fg = (attr & 0x0f000000) ? ri->ri_devcmap[1] : ri->ri_devcmap[0]; - - /* If fg and bg match this becomes a space character */ - if (fg == bg || uc == ' ') { - while (height--) { - /* XXX alignment?! */ - *(uint16_t *)rp = bg; - rp += rs; - if (ri->ri_hwbits) { - *(uint16_t *)hrp = bg; - hrp += rs; - } - } - } else { - fr = FONT_GLYPH(uc, font, ri); - fs = font->stride; - - /* NOT fontbits if bg is white */ - if (bg) { - while (height--) { - rp[0] = ~fr[0]; - rp[1] = ~fr[1]; - rp += rs; - if (ri->ri_hwbits) { - hrp[0] = ~fr[0]; - hrp[1] = ~fr[1]; - hrp += rs; - } - fr += fs; - } - } else { - while (height--) { - rp[0] = fr[0]; - rp[1] = fr[1]; - rp += rs; - if (ri->ri_hwbits) { - hrp[0] = fr[0]; - hrp[1] = fr[1]; - hrp += rs; - } - fr += fs; - } - } - } - - /* Do underline */ - if ((attr & WSATTR_UNDERLINE) != 0) { - /* XXX alignment?! */ - *(uint16_t *)(rp - (ri->ri_stride << 1)) = fg; - if (ri->ri_hwbits) { - *(uint16_t *)(hrp - (ri->ri_stride << 1)) = fg; - } - } -} #endif /* !RASOPS_SMALL */ /* diff --git a/sys/dev/rasops/rasops1_putchar_width.h b/sys/dev/rasops/rasops1_putchar_width.h new file mode 100644 index 00000000000..592a9faab5f --- /dev/null +++ b/sys/dev/rasops/rasops1_putchar_width.h @@ -0,0 +1,137 @@ +/* $NetBSD: rasops1_putchar_width.h,v 1.1 2019/07/29 02:57:41 rin Exp $ */ + +/* NetBSD: rasops1.c,v 1.28 2019/07/25 03:02:44 rin Exp */ +/*- + * Copyright (c) 1999 The NetBSD Foundation, Inc. + * All rights reserved. + * + * This code is derived from software contributed to The NetBSD Foundation + * by Andrew Doran. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS + * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED + * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR + * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS + * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + */ + +#if RASOPS_WIDTH != 8 && RASOPS_WIDTH != 16 +#error "Width not supported" +#endif + +#define PUTCHAR_WIDTH1(width) rasops1_putchar ## width +#define PUTCHAR_WIDTH(width) PUTCHAR_WIDTH1(width) + +#if RASOPS_WIDTH == 8 +#define COPY_UNIT uint8_t +#define GET_GLYPH tmp = fr[0] +#endif + +#if RASOPS_WIDTH == 16 +/* + * rp and hrp are always half-word aligned, whereas + * fr may not be aligned in half-word boundary. + */ +#define COPY_UNIT uint16_t +# if BYTE_ORDER == BIG_ENDIAN +#define GET_GLYPH tmp = (fr[0] << 8) | fr[1] +# else +#define GET_GLYPH tmp = fr[0] | (fr[1] << 8) +# endif +#endif /* RASOPS_WIDTH == 16 */ + +/* + * Width-optimized putchar function. + */ +static void +PUTCHAR_WIDTH(RASOPS_WIDTH)(void *cookie, int row, int col, u_int uc, long attr) +{ + struct rasops_info *ri = (struct rasops_info *)cookie; + struct wsdisplay_font *font = PICK_FONT(ri, uc); + int height, fs, rs, bg, fg; + uint8_t *fr; + COPY_UNIT *rp, *hrp, tmp; + + hrp = NULL; /* XXX GCC */ + +#ifdef RASOPS_CLIPPING + /* Catches 'row < 0' case too */ + if ((unsigned)row >= (unsigned)ri->ri_rows) + return; + + if ((unsigned)col >= (unsigned)ri->ri_cols) + return; +#endif + + rp = (COPY_UNIT *)(ri->ri_bits + row * ri->ri_yscale + + col * sizeof(COPY_UNIT)); + if (ri->ri_hwbits) + hrp = (COPY_UNIT *)(ri->ri_hwbits + row * ri->ri_yscale + + col * sizeof(COPY_UNIT)); + height = font->fontheight; + rs = ri->ri_stride; + + bg = (attr & 0x000f0000) ? ri->ri_devcmap[1] : ri->ri_devcmap[0]; + fg = (attr & 0x0f000000) ? ri->ri_devcmap[1] : ri->ri_devcmap[0]; + + /* If fg and bg match this becomes a space character */ + if (uc == ' ' || fg == bg) { + while (height--) { + *rp = bg; + DELTA(rp, rs, COPY_UNIT *); + } + if (ri->ri_hwbits) { + while (height--) { + *hrp = bg; + DELTA(hrp, rs, COPY_UNIT *); + } + } + } else { + fr = FONT_GLYPH(uc, font, ri); + fs = font->stride; + + while (height--) { + GET_GLYPH; + if (bg) + tmp = ~tmp; + *rp = tmp; + DELTA(rp, rs, COPY_UNIT *); + if (ri->ri_hwbits) { + *hrp = tmp; + DELTA(hrp, rs, COPY_UNIT *); + } + fr += fs; + } + } + + /* Do underline */ + if ((attr & WSATTR_UNDERLINE) != 0) { + DELTA(rp, -(ri->ri_stride << 1), COPY_UNIT *); + *rp = fg; + if (ri->ri_hwbits) { + DELTA(hrp, -(ri->ri_stride << 1), COPY_UNIT *); + *hrp = fg; + } + } +} + +#undef PUTCHAR_WIDTH1 +#undef PUTCHAR_WIDTH + +#undef COPY_UNIT +#undef GET_GLYPH |
