-/* $OpenBSD: lunafb.c,v 1.18 2013/12/30 07:33:40 aoyama Exp $ */
+/* $OpenBSD: lunafb.c,v 1.19 2014/01/02 15:30:34 aoyama Exp $ */
/* $NetBSD: lunafb.c,v 1.7.6.1 2002/08/07 01:48:34 lukem Exp $ */
/*-
#define OMFB_RAMDAC 0xC1100000 /* Bt454/Bt458 RAMDAC */
#define OMFB_SIZE (0xB1300000 - 0xB1080000 + PAGE_SIZE)
+struct hwcmap {
+#define CMAP_SIZE 256
+ u_int8_t r[CMAP_SIZE];
+ u_int8_t g[CMAP_SIZE];
+ u_int8_t b[CMAP_SIZE];
+};
+
+static const struct {
+ u_int8_t r;
+ u_int8_t g;
+ u_int8_t b;
+} ansicmap[16] = {
+ { 0, 0, 0},
+ { 0x80, 0, 0},
+ { 0, 0x80, 0},
+ { 0x80, 0x80, 0},
+ { 0, 0, 0x80},
+ { 0x80, 0, 0x80},
+ { 0, 0x80, 0x80},
+ { 0xc0, 0xc0, 0xc0},
+ { 0x80, 0x80, 0x80},
+ { 0xff, 0, 0},
+ { 0, 0xff, 0},
+ { 0xff, 0xff, 0},
+ { 0, 0, 0xff},
+ { 0xff, 0, 0xff},
+ { 0, 0xff, 0xff},
+ { 0xff, 0xff, 0xff},
+};
+
struct om_hwdevconfig {
int dc_wid; /* width of frame buffer */
int dc_ht; /* height of frame buffer */
int dc_depth; /* depth, bits per pixel */
int dc_rowbytes; /* bytes in a FB scan line */
+ int dc_depth_checked; /* depth is really checked or not */
int dc_cmsize; /* colormap size */
+ struct hwcmap dc_cmap; /* software copy of colormap */
vaddr_t dc_videobase; /* base of flat frame buffer */
struct rasops_info dc_ri; /* raster blitter variables */
};
-struct hwcmap {
-#define CMAP_SIZE 256
- u_int8_t r[CMAP_SIZE];
- u_int8_t g[CMAP_SIZE];
- u_int8_t b[CMAP_SIZE];
-};
-
struct omfb_softc {
struct device sc_dev; /* base device */
struct om_hwdevconfig *sc_dc; /* device configuration */
- struct hwcmap sc_cmap; /* software copy of colormap */
int nscreens;
};
void omfb_getdevconfig(paddr_t, struct om_hwdevconfig *);
/* in omrasops.c */
-int om_cursor(void *, int, int, int);
-int om_putchar(void *, int, int, u_int, long);
int om_copycols(void *, int, int, int, int);
int om_copyrows(void *, int, int, int num);
int om_erasecols(void *, int, int, int, long);
int om_eraserows(void *, int, int, long);
+void setup_omrasops1(struct rasops_info *);
+void setup_omrasops4(struct rasops_info *);
struct wsscreen_descr omfb_stdscreen = {
"std"
if (hwplanebits == 0)
return (0);
#endif
-
- /*
- * Check how many planes we have. This is for 1, 4, and 8 bpp
- * boards, must be checked different way for 24 bpp board...
- */
- if (hwplanebits > 0) {
- int i;
- u_int32_t *max, save;
-
- for (i = 0; i < 8; i++) {
- max = (u_int32_t *)trunc_page(OMFB_FB_RADDR
- + OMFB_FB_PLANESIZE * i);
- save = *max;
- *(volatile uint32_t *)max = 0x5a5a5a5a;
- if (*max != 0x5a5a5a5a)
- break;
- *max = save;
- }
- hwplanebits = i; /* should be 1, 4, or 8 */
- }
return (1);
}
printf(": %d x %d, %dbpp\n", sc->sc_dc->dc_wid, sc->sc_dc->dc_ht,
hwplanebits);
- /* WHITE on BLACK */
- memset(&sc->sc_cmap, 255, sizeof(struct hwcmap));
- sc->sc_cmap.r[0] = sc->sc_cmap.g[0] = sc->sc_cmap.b[0] = 0;
-
waa.console = omfb_console;
waa.scrdata = &omfb_screenlist;
waa.accessops = &omfb_accessops;
if (offset >= 0 && offset < OMFB_SIZE)
cookie = (paddr_t)(trunc_page(dc->dc_videobase) + offset);
#else
- if (offset >= 0 && offset < dc->dc_rowbytes * dc->dc_ht)
+ if (offset >= 0 && offset < dc->dc_rowbytes * dc->dc_ht * hwplanebits)
cookie = (paddr_t)(trunc_page(OMFB_FB_RADDR) + offset);
#endif
return cookie;
if (index >= cmsize || count > cmsize - index)
return (EINVAL);
- error = copyout(&sc->sc_cmap.r[index], p->red, count);
+ error = copyout(&sc->sc_dc->dc_cmap.r[index], p->red, count);
if (error != 0)
return (error);
- error = copyout(&sc->sc_cmap.g[index], p->green, count);
+ error = copyout(&sc->sc_dc->dc_cmap.g[index], p->green, count);
if (error != 0)
return (error);
- error = copyout(&sc->sc_cmap.b[index], p->blue, count);
+ error = copyout(&sc->sc_dc->dc_cmap.b[index], p->blue, count);
if (error != 0)
return (error);
struct omfb_softc *sc;
struct wsdisplay_cmap *p;
{
+ struct hwcmap cmap;
u_int index = p->index, count = p->count;
unsigned int cmsize, i;
int error;
if (index >= cmsize || count > cmsize - index)
return (EINVAL);
- error = copyin(p->red, &sc->sc_cmap.r[index], count);
+ error = copyin(p->red, &cmap.r[index], count);
if (error != 0)
return (error);
- error = copyin(p->green, &sc->sc_cmap.g[index], count);
+ error = copyin(p->green, &cmap.g[index], count);
if (error != 0)
return (error);
- error = copyin(p->blue, &sc->sc_cmap.b[index], count);
+ error = copyin(p->blue, &cmap.b[index], count);
if (error != 0)
return (error);
+ memcpy(&sc->sc_dc->dc_cmap.r[index], &cmap.r[index], count);
+ memcpy(&sc->sc_dc->dc_cmap.g[index], &cmap.g[index], count);
+ memcpy(&sc->sc_dc->dc_cmap.b[index], &cmap.b[index], count);
+
if (hwplanebits == 4) {
struct bt454 *odac = (struct bt454 *)OMFB_RAMDAC;
odac->bt_addr = (u_int8_t)index;
for (i = index; i < index + count; i++) {
- odac->bt_cmap = sc->sc_cmap.r[i];
- odac->bt_cmap = sc->sc_cmap.g[i];
- odac->bt_cmap = sc->sc_cmap.b[i];
+ odac->bt_cmap = sc->sc_dc->dc_cmap.r[i];
+ odac->bt_cmap = sc->sc_dc->dc_cmap.g[i];
+ odac->bt_cmap = sc->sc_dc->dc_cmap.b[i];
}
}
else if (hwplanebits == 8) {
struct bt458 *ndac = (struct bt458 *)OMFB_RAMDAC;
ndac->bt_addr = (u_int8_t)index;
for (i = index; i < index + count; i++) {
- ndac->bt_cmap = sc->sc_cmap.r[i];
- ndac->bt_cmap = sc->sc_cmap.g[i];
- ndac->bt_cmap = sc->sc_cmap.b[i];
+ ndac->bt_cmap = sc->sc_dc->dc_cmap.r[i];
+ ndac->bt_cmap = sc->sc_dc->dc_cmap.g[i];
+ ndac->bt_cmap = sc->sc_dc->dc_cmap.b[i];
}
}
return (0);
u_int32_t u;
} rfcnt;
-#if 0 /* Workaround for making Xorg mono server work */
+ /*
+ * If this is the first time call, check how many planes we really
+ * have. This method is for 1, 4, and 8 bpp boards, must be checked
+ * different way for 24 bpp board...
+ */
+ if ((hwplanebits > 0) && (dc->dc_depth_checked == 0)) {
+ int i;
+ u_int32_t *max, save;
+
+ for (i = 0; i < 8; i++) {
+ max = (u_int32_t *)trunc_page(OMFB_FB_RADDR
+ + OMFB_FB_PLANESIZE * i);
+ save = *max;
+ *(volatile uint32_t *)max = 0x5a5a5a5a;
+ if (*max != 0x5a5a5a5a)
+ break;
+ *max = save;
+ }
+ hwplanebits = i; /* should be 1, 4, or 8 */
+
+ dc->dc_depth_checked = 1;
+ }
+
+#if 1 /* Workaround for making Xorg mono server work */
switch (hwplanebits) {
case 8:
bpp = 8; /* XXX check monochrome bit in DIPSW */
struct bt454 *odac = (struct bt454 *)OMFB_RAMDAC;
odac->bt_addr = 0;
- odac->bt_cmap = 0;
- odac->bt_cmap = 0;
- odac->bt_cmap = 0;
- for (i = 1; i < 16; i++) {
- odac->bt_cmap = 255;
- odac->bt_cmap = 255;
- odac->bt_cmap = 255;
+ for (i = 0; i < 16; i++) {
+ odac->bt_cmap = dc->dc_cmap.r[i] = ansicmap[i].r;
+ odac->bt_cmap = dc->dc_cmap.g[i] = ansicmap[i].g;
+ odac->bt_cmap = dc->dc_cmap.b[i] = ansicmap[i].b;
}
} else if (hwplanebits == 8) {
struct bt458 *ndac = (struct bt458 *)OMFB_RAMDAC;
- /* Initialize the Bt458 */
+ /*
+ * Initialize the Bt458. When we write to control registers,
+ * the address is not incremented automatically. So we specify
+ * it ourselves for each control register.
+ */
ndac->bt_addr = 0x04;
ndac->bt_ctrl = 0xff; /* all planes will be read */
ndac->bt_addr = 0x05;
ndac->bt_addr = 0x07;
ndac->bt_ctrl = 0x00; /* no test mode */
+ /*
+ * Set ANSI 16 colors. We only supports 4bpp console right
+ * now, repeat 16 colors in 256 colormap.
+ */
ndac->bt_addr = 0;
- ndac->bt_cmap = 0;
- ndac->bt_cmap = 0;
- ndac->bt_cmap = 0;
- for (i = 1; i < 256; i++) {
- ndac->bt_cmap = 255;
- ndac->bt_cmap = 255;
- ndac->bt_cmap = 255;
+ for (i = 0; i < 256; i++) {
+ ndac->bt_cmap = dc->dc_cmap.r[i] = ansicmap[i % 16].r;
+ ndac->bt_cmap = dc->dc_cmap.g[i] = ansicmap[i % 16].g;
+ ndac->bt_cmap = dc->dc_cmap.b[i] = ansicmap[i % 16].b;
}
}
rasops_init(ri, 35, 80);
- omfb_stdscreen.ncols = ri->ri_cols;
- omfb_stdscreen.nrows = ri->ri_rows;
- ri->ri_ops.cursor = om_cursor;
- ri->ri_ops.putchar = om_putchar;
ri->ri_ops.copycols = om_copycols;
ri->ri_ops.erasecols = om_erasecols;
ri->ri_ops.copyrows = om_copyrows;
ri->ri_ops.eraserows = om_eraserows;
+ omfb_stdscreen.ncols = ri->ri_cols;
+ omfb_stdscreen.nrows = ri->ri_rows;
omfb_stdscreen.textops = &ri->ri_ops;
omfb_stdscreen.fontwidth = ri->ri_font->fontwidth;
omfb_stdscreen.fontheight = ri->ri_font->fontheight;
- omfb_stdscreen.capabilities = ri->ri_caps & ~WSSCREEN_UNDERLINE;
+
+ /* set up depth-depend functions and so on */
+ if ((hwplanebits == 4) || (hwplanebits == 8)) {
+ setup_omrasops4(ri);
+ } else {
+ setup_omrasops1(ri);
+ }
}
int
-/* $OpenBSD: maskbits.h,v 1.1 2013/11/16 22:45:37 aoyama Exp $ */
+/* $OpenBSD: maskbits.h,v 1.2 2014/01/02 15:30:34 aoyama Exp $ */
/* $NetBSD: maskbits.h,v 1.3 1997/03/31 07:37:28 scottr Exp $ */
/*-
/* Get a number of bits ( <= 32 ) from *sp and store in dw */
#define OMFB_GETBITS(sp, x, w, dw) \
do { \
- dw = OMFB_MBL(R(sp), (x)); \
+ dw = OMFB_MBL(*(sp), (x)); \
if (((x) + (w)) > 32) \
- dw |= (OMFB_MBR(R(sp + 1), 32 - (x))); \
+ dw |= (OMFB_MBR(*(sp + 1), 32 - (x))); \
} while(0);
/* Put a number of bits ( <= 32 ) from sw to *dp */
\
if (n <= 0) { \
n = rasops_pmask[x & 31][w & 31]; \
- W(dp) = ((R(dp) & ~n) | (OMFB_MBR(sw, x) & n)); \
+ *(dp) = (*(dp) & ~n) | (OMFB_MBR(sw, x) & n); \
} else { \
- W(dp) = ((R(dp) & rasops_rmask[x]) \
- | (OMFB_MBR(sw, x))); \
- W(dp + 1) = ((R(dp + 1) & rasops_lmask[n]) \
- | (OMFB_MBL(sw, 32-(x)) & rasops_rmask[n])); \
+ *(dp) = (*(dp) & rasops_rmask[x]) \
+ | (OMFB_MBR(sw, x)); \
+ *(dp + 1) = (*(dp + 1) & rasops_lmask[n]) \
+ | (OMFB_MBL(sw, 32-(x)) & rasops_rmask[n]); \
} \
} while(0);
-/* $OpenBSD: omrasops.c,v 1.10 2013/11/16 22:45:37 aoyama Exp $ */
+/* $OpenBSD: omrasops.c,v 1.11 2014/01/02 15:30:34 aoyama Exp $ */
/* $NetBSD: omrasops.c,v 1.1 2000/01/05 08:48:56 nisimura Exp $ */
/*-
#include <luna88k/dev/omrasops.h>
/* wscons emulator operations */
-int om_cursor(void *, int, int, int);
-int om_putchar(void *, int, int, u_int, long);
int om_copycols(void *, int, int, int, int);
int om_copyrows(void *, int, int, int num);
int om_erasecols(void *, int, int, int, long);
int om_eraserows(void *, int, int, long);
+int om1_cursor(void *, int, int, int);
+int om1_putchar(void *, int, int, u_int, long);
+int om4_cursor(void *, int, int, int);
+int om4_putchar(void *, int, int, u_int, long);
-/* internal functions (for 1bpp, in omrasops1.c) */
-int om_windowmove1(struct rasops_info *, u_int16_t, u_int16_t,
- u_int16_t, u_int16_t, u_int16_t, u_int16_t, int16_t,
- int16_t /* ignored */);
+/* depth-depended setup functions */
+void setup_omrasops1(struct rasops_info *);
+void setup_omrasops4(struct rasops_info *);
+
+/* internal functions for 1bpp/4bpp */
+int om1_windowmove(struct rasops_info *, u_int16_t, u_int16_t, u_int16_t,
+ u_int16_t, u_int16_t, u_int16_t, int16_t, int16_t);
+int om4_windowmove(struct rasops_info *, u_int16_t, u_int16_t, u_int16_t,
+ u_int16_t, u_int16_t, u_int16_t, int16_t, int16_t);
+
+/* MI function in src/sys/dev/rasops/rasops.c */
+int rasops_alloc_cattr(void *, int, int, int, long *);
+
+static int (*om_windowmove)(struct rasops_info *, u_int16_t, u_int16_t,
+ u_int16_t, u_int16_t, u_int16_t, u_int16_t, int16_t, int16_t);
+
+extern struct wsscreen_descr omfb_stdscreen;
#define ALL1BITS (~0U)
#define ALL0BITS (0U)
/*
* Blit a character at the specified co-ordinates.
+ * - 1bpp version -
*/
int
-om_putchar(void *cookie, int row, int startcol, u_int uc, long attr)
+om1_putchar(void *cookie, int row, int startcol, u_int uc, long attr)
{
struct rasops_info *ri = cookie;
u_int8_t *p;
glyph = (glyph << 8) | *fb++;
glyph <<= (4 - ri->ri_font->stride) * NBBY;
glyph = (glyph >> align) ^ inverse;
- W(p) = (R(p) & ~lmask) | (glyph & lmask);
+ *W(p) = (*R(p) & ~lmask) | (glyph & lmask);
p += scanspan;
height--;
}
- }
- else {
+ } else {
u_int8_t *q = p;
u_int32_t lhalf, rhalf;
glyph = (glyph << 8) | *fb++;
glyph <<= (4 - ri->ri_font->stride) * NBBY;
lhalf = (glyph >> align) ^ inverse;
- W(p) = (R(p) & ~lmask) | (lhalf & lmask);
+ *W(p) = (*R(p) & ~lmask) | (lhalf & lmask);
+
p += BYTESDONE;
+
rhalf = (glyph << (BLITWIDTH - align)) ^ inverse;
- W(p) = (rhalf & rmask) | (R(p) & ~rmask);
+ *W(p) = (rhalf & rmask) | (*R(p) & ~rmask);
+
+ p = (q += scanspan);
+ height--;
+ }
+ }
+
+ return 0;
+}
+
+/*
+ * Blit a character at the specified co-ordinates
+ * - 4bpp version -
+ */
+int
+om4_putchar(void *cookie, int row, int startcol, u_int uc, long attr)
+{
+ struct rasops_info *ri = cookie;
+ u_int8_t *p;
+ int scanspan, startx, height, width, align, y;
+ u_int32_t lmask, rmask, glyph, glyphbg, fgpat, bgpat;
+ int i, fg, bg;
+ u_int8_t *fb;
+
+ scanspan = ri->ri_stride;
+ y = ri->ri_font->fontheight * row;
+ startx = ri->ri_font->fontwidth * startcol;
+ height = ri->ri_font->fontheight;
+ fb = (u_int8_t *)ri->ri_font->data +
+ (uc - ri->ri_font->firstchar) * ri->ri_fontscale;
+ ri->ri_ops.unpack_attr(cookie, attr, &fg, &bg, NULL);
+
+ p = (u_int8_t *)ri->ri_bits + y * scanspan + ((startx / 32) * 4);
+ align = startx & ALIGNMASK;
+ width = ri->ri_font->fontwidth + align;
+ lmask = ALL1BITS >> align;
+ rmask = ALL1BITS << (-width & ALIGNMASK);
+ if (width <= BLITWIDTH) {
+ lmask &= rmask;
+ while (height > 0) {
+ glyph = 0;
+ for (i = ri->ri_font->stride; i != 0; i--)
+ glyph = (glyph << 8) | *fb++;
+ glyph <<= (4 - ri->ri_font->stride) * NBBY;
+ glyph = (glyph >> align);
+ glyphbg = glyph ^ ALL1BITS;
+
+ fgpat = (fg & 0x01) ? glyph : 0;
+ bgpat = (bg & 0x01) ? glyphbg : 0;
+ *P0(p) = (*P0(p) & ~lmask) | ((fgpat | bgpat) & lmask);
+ fgpat = (fg & 0x02) ? glyph : 0;
+ bgpat = (bg & 0x02) ? glyphbg : 0;
+ *P1(p) = (*P1(p) & ~lmask) | ((fgpat | bgpat) & lmask);
+ fgpat = (fg & 0x04) ? glyph : 0;
+ bgpat = (bg & 0x04) ? glyphbg : 0;
+ *P2(p) = (*P2(p) & ~lmask) | ((fgpat | bgpat) & lmask);
+ fgpat = (fg & 0x08) ? glyph : 0;
+ bgpat = (bg & 0x08) ? glyphbg : 0;
+ *P3(p) = (*P3(p) & ~lmask) | ((fgpat | bgpat) & lmask);
+
+ p += scanspan;
+ height--;
+ }
+ } else {
+ u_int8_t *q = p;
+ u_int32_t lhalf, rhalf;
+ u_int32_t lhalfbg, rhalfbg;
+
+ while (height > 0) {
+ glyph = 0;
+ for (i = ri->ri_font->stride; i != 0; i--)
+ glyph = (glyph << 8) | *fb++;
+ glyph <<= (4 - ri->ri_font->stride) * NBBY;
+ lhalf = (glyph >> align);
+ lhalfbg = lhalf ^ ALL1BITS;
+
+ fgpat = (fg & 0x01) ? lhalf : 0;
+ bgpat = (bg & 0x01) ? lhalfbg : 0;
+ *P0(p) = (*P0(p) & ~lmask) | ((fgpat | bgpat) & lmask);
+ fgpat = (fg & 0x02) ? lhalf : 0;
+ bgpat = (bg & 0x02) ? lhalfbg : 0;
+ *P1(p) = (*P1(p) & ~lmask) | ((fgpat | bgpat) & lmask);
+ fgpat = (fg & 0x04) ? lhalf : 0;
+ bgpat = (bg & 0x04) ? lhalfbg : 0;
+ *P2(p) = (*P2(p) & ~lmask) | ((fgpat | bgpat) & lmask);
+ fgpat = (fg & 0x08) ? lhalf : 0;
+ bgpat = (bg & 0x08) ? lhalfbg : 0;
+ *P3(p) = (*P3(p) & ~lmask) | ((fgpat | bgpat) & lmask);
+
+ p += BYTESDONE;
+
+ rhalf = (glyph << (BLITWIDTH - align));
+ rhalfbg = rhalf ^ ALL1BITS;
+
+ fgpat = (fg & 0x01) ? rhalf : 0;
+ bgpat = (bg & 0x01) ? rhalfbg : 0;
+ *P0(p) = ((fgpat | bgpat) & rmask) | (*P0(p) & ~rmask);
+ fgpat = (fg & 0x02) ? rhalf : 0;
+ bgpat = (bg & 0x02) ? rhalfbg : 0;
+ *P1(p) = ((fgpat | bgpat) & rmask) | (*P1(p) & ~rmask);
+ fgpat = (fg & 0x04) ? rhalf : 0;
+ bgpat = (bg & 0x04) ? rhalfbg : 0;
+ *P2(p) = ((fgpat | bgpat) & rmask) | (*P2(p) & ~rmask);
+ fgpat = (fg & 0x08) ? rhalf : 0;
+ bgpat = (bg & 0x08) ? rhalfbg : 0;
+ *P3(p) = ((fgpat | bgpat) & rmask) | (*P3(p) & ~rmask);
p = (q += scanspan);
height--;
* If this is too tricky for the simple raster ops engine,
* pass the fun to rasops.
*/
- if (om_windowmove1(ri, scol, srow, scol, srow, snum,
+ if ((*om_windowmove)(ri, scol, srow, scol, srow, snum,
ri->ri_font->fontheight, RR_CLEAR, 0xff ^ bg) != 0)
rasops_erasecols(cookie, row, col, num, attr);
bg ^= 0xff;
if (num == ri->ri_rows && (ri->ri_flg & RI_FULLCLEAR)) {
- rc = om_windowmove1(ri, 0, 0, 0, 0, ri->ri_width, ri->ri_height,
- RR_CLEAR, bg);
+ rc = (*om_windowmove)(ri, 0, 0, 0, 0, ri->ri_width,
+ ri->ri_height, RR_CLEAR, bg);
} else {
srow = row * ri->ri_font->fontheight + ri->ri_yorigin;
snum = num * ri->ri_font->fontheight;
- rc = om_windowmove1(ri, ri->ri_xorigin, srow, ri->ri_xorigin,
+ rc = (*om_windowmove)(ri, ri->ri_xorigin, srow, ri->ri_xorigin,
srow, ri->ri_emuwidth, snum, RR_CLEAR, bg);
}
if (rc != 0)
src *= ri->ri_font->fontheight;
dst *= ri->ri_font->fontheight;
- om_windowmove1(ri, ri->ri_xorigin, ri->ri_yorigin + src,
+ (*om_windowmove)(ri, ri->ri_xorigin, ri->ri_yorigin + src,
ri->ri_xorigin, ri->ri_yorigin + dst,
ri->ri_emuwidth, n, RR_COPY, 0xff);
dst *= ri->ri_font->fontwidth;
row *= ri->ri_font->fontheight;
- om_windowmove1(ri, ri->ri_xorigin + src, ri->ri_yorigin + row,
+ (*om_windowmove)(ri, ri->ri_xorigin + src, ri->ri_yorigin + row,
ri->ri_xorigin + dst, ri->ri_yorigin + row,
n, ri->ri_font->fontheight, RR_COPY, 0xff);
/*
* Position|{enable|disable} the cursor at the specified location.
+ * - 1bpp version -
*/
int
-om_cursor(void *cookie, int on, int row, int col)
+om1_cursor(void *cookie, int on, int row, int col)
{
struct rasops_info *ri = cookie;
u_int8_t *p;
if (width <= BLITWIDTH) {
lmask &= rmask;
while (height > 0) {
- image = R(p);
- W(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ image = *R(p);
+ *W(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
p += scanspan;
height--;
}
+ } else {
+ u_int8_t *q = p;
+
+ while (height > 0) {
+ image = *R(p);
+ *W(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ p += BYTESDONE;
+
+ image = *R(p);
+ *W(p) = ((image ^ ALL1BITS) & rmask) | (image & ~rmask);
+ p = (q += scanspan);
+ height--;
+ }
+ }
+ ri->ri_flg ^= RI_CURSOR;
+
+ return 0;
+}
+
+/*
+ * Position|{enable|disable} the cursor at the specified location
+ * - 4bpp version -
+ */
+int
+om4_cursor(void *cookie, int on, int row, int col)
+{
+ struct rasops_info *ri = cookie;
+ u_int8_t *p;
+ int scanspan, startx, height, width, align, y;
+ u_int32_t lmask, rmask, image;
+
+ if (!on) {
+ /* make sure it's on */
+ if ((ri->ri_flg & RI_CURSOR) == 0)
+ return 0;
+
+ row = ri->ri_crow;
+ col = ri->ri_ccol;
+ } else {
+ /* unpaint the old copy. */
+ ri->ri_crow = row;
+ ri->ri_ccol = col;
}
- else {
+
+ scanspan = ri->ri_stride;
+ y = ri->ri_font->fontheight * row;
+ startx = ri->ri_font->fontwidth * col;
+ height = ri->ri_font->fontheight;
+
+ p = (u_int8_t *)ri->ri_bits + y * scanspan + ((startx / 32) * 4);
+ align = startx & ALIGNMASK;
+ width = ri->ri_font->fontwidth + align;
+ lmask = ALL1BITS >> align;
+ rmask = ALL1BITS << (-width & ALIGNMASK);
+ if (width <= BLITWIDTH) {
+ lmask &= rmask;
+ while (height > 0) {
+ image = *P0(p);
+ *P0(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ image = *P1(p);
+ *P1(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ image = *P2(p);
+ *P2(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ image = *P3(p);
+ *P3(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ p += scanspan;
+ height--;
+ }
+ } else {
u_int8_t *q = p;
while (height > 0) {
- image = R(p);
- W(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ image = *P0(p);
+ *P0(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ image = *P1(p);
+ *P1(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ image = *P2(p);
+ *P2(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+ image = *P3(p);
+ *P3(p) = (image & ~lmask) | ((image ^ ALL1BITS) & lmask);
+
p += BYTESDONE;
- image = R(p);
- W(p) = ((image ^ ALL1BITS) & rmask) | (image & ~rmask);
+
+ image = *P0(p);
+ *P0(p) = ((image ^ ALL1BITS) & rmask) | (image & ~rmask);
+ image = *P1(p);
+ *P1(p) = ((image ^ ALL1BITS) & rmask) | (image & ~rmask);
+ image = *P2(p);
+ *P2(p) = ((image ^ ALL1BITS) & rmask) | (image & ~rmask);
+ image = *P3(p);
+ *P3(p) = ((image ^ ALL1BITS) & rmask) | (image & ~rmask);
p = (q += scanspan);
height--;
return 0;
}
+
+/*
+ * After calling rasops_init(), set up our depth-depend emulops,
+ * block move function and capabilities.
+ */
+void
+setup_omrasops1(struct rasops_info *ri)
+{
+ om_windowmove = om1_windowmove;
+ ri->ri_ops.cursor = om1_cursor;
+ ri->ri_ops.putchar = om1_putchar;
+ omfb_stdscreen.capabilities
+ = ri->ri_caps & ~WSSCREEN_UNDERLINE;
+}
+
+void
+setup_omrasops4(struct rasops_info *ri)
+{
+ om_windowmove = om4_windowmove;
+ ri->ri_ops.cursor = om4_cursor;
+ ri->ri_ops.putchar = om4_putchar;
+ omfb_stdscreen.capabilities
+ = WSSCREEN_HILIT | WSSCREEN_WSCOLORS | WSSCREEN_REVERSE;
+ /*
+ * Since we set ri->ri_depth == 1, rasops_init() set
+ * rasops_alloc_mattr for us. But we use the color version,
+ * rasops_alloc_cattr, on 4bpp/8bpp frame buffer.
+ */
+ ri->ri_ops.alloc_attr = rasops_alloc_cattr;
+}
/*
* Base addresses of LUNA's frame buffer
- * XXX: We consider only 1bpp for now
+ * XXX: We consider only 1bpp and 4bpp for now
*/
#define OMFB_FB_WADDR 0xB1080008 /* common plane */
#define OMFB_FB_RADDR 0xB10C0008 /* plane #0 */
/*
* Helper macros
*/
-#define W(p) (*(u_int32_t *)(p))
-#define R(p) (*(u_int32_t *)((u_int8_t *)(p) + 0x40000))
+#define W(addr) ((u_int32_t *)(addr))
+#define R(addr) ((u_int32_t *)((u_int8_t *)(addr) + 0x40000))
+#define P0(addr) ((u_int32_t *)((u_int8_t *)(addr) + 0x40000))
+#define P1(addr) ((u_int32_t *)((u_int8_t *)(addr) + 0x80000))
+#define P2(addr) ((u_int32_t *)((u_int8_t *)(addr) + 0xC0000))
+#define P3(addr) ((u_int32_t *)((u_int8_t *)(addr) + 0x100000))
/*
* Replacement Rules (rops) (derived from hp300)
-/* $OpenBSD: omrasops1.c,v 1.1 2013/11/16 22:45:37 aoyama Exp $ */
+/* $OpenBSD: omrasops1.c,v 1.2 2014/01/02 15:30:34 aoyama Exp $ */
/*
* Copyright (c) 2005, Miodrag Vallat.
*/
/*
- * Graphics routines for OMRON LUNA 1bpp frame buffer. On LUNA's frame
- * buffer, pixels are not byte-addressed.
+ * Graphics routines for OMRON LUNA 1bpp and 4bpp frame buffer.
+ * On LUNA's frame buffer, pixels are not byte-addressed.
*
* Based on src/sys/arch/hp300/dev/diofb_mono.c
*/
#include <dev/rasops/rasops_masks.h>
#include <luna88k/dev/maskbits.h>
+#include <luna88k/dev/omrasops.h>
-/* Prototypes */
-int om_windowmove1(struct rasops_info *, u_int16_t, u_int16_t,
+/* prototypes */
+int om1_windowmove(struct rasops_info *, u_int16_t, u_int16_t,
+ u_int16_t, u_int16_t, u_int16_t, u_int16_t, int16_t,
+ int16_t /* ignored */);
+int om4_windowmove(struct rasops_info *, u_int16_t, u_int16_t,
u_int16_t, u_int16_t, u_int16_t, u_int16_t, int16_t,
int16_t /* ignored */);
+/*
+ * Block-move function - 1bpp version
+ */
int
-om_windowmove1(struct rasops_info *ri, u_int16_t sx, u_int16_t sy,
+om1_windowmove(struct rasops_info *ri, u_int16_t sx, u_int16_t sy,
u_int16_t dx, u_int16_t dy, u_int16_t cx, u_int16_t cy, int16_t rop,
int16_t planemask /* ignored */)
{
dstBit = dx & 0x1f;
while (cy--) {
- getandputrop(psrc, srcBit, dstBit, cx, pdst, rop);
+ getandputrop(R(psrc), srcBit, dstBit, cx, W(pdst), rop);
pdst += width;
psrc += width;
}
pdst = pdstLine;
if (startmask) {
- getandputrop(psrc, (sx & 0x1f),
- (dx & 0x1f), nstart, pdst, rop);
+ getandputrop(R(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, W(pdst), rop);
pdst++;
if (srcStartOver)
psrc++;
if (rop == RR_CLEAR)
W(pdst) = 0;
else
- getunalignedword(psrc,
- xoffSrc, *pdst);
+ getunalignedword(R(psrc),
+ xoffSrc, *W(pdst));
pdst++;
psrc++;
}
}
if (endmask) {
- getandputrop(psrc, xoffSrc, 0, nend,
- pdst, rop);
+ getandputrop(R(psrc), xoffSrc, 0, nend,
+ W(pdst), rop);
}
pdstLine += width;
pdst = pdstLine;
if (endmask) {
- getandputrop(psrc, xoffSrc, 0, nend,
- pdst, rop);
+ getandputrop(R(psrc), xoffSrc, 0, nend,
+ W(pdst), rop);
}
nl = nlMiddle + 1;
if (rop == RR_CLEAR)
W(pdst) = 0;
else
- getunalignedword(psrc, xoffSrc,
- *pdst);
+ getunalignedword(R(psrc), xoffSrc,
+ *W(pdst));
+ }
+
+ if (startmask) {
+ if (srcStartOver)
+ --psrc;
+ --pdst;
+ getandputrop(R(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, W(pdst), rop);
+ }
+
+ pdstLine += width;
+ psrcLine += width;
+ }
+ }
+ }
+
+ return (0);
+}
+
+/*
+ * Block-move function - 4bpp version
+ */
+int
+om4_windowmove(struct rasops_info *ri, u_int16_t sx, u_int16_t sy,
+ u_int16_t dx, u_int16_t dy, u_int16_t cx, u_int16_t cy, int16_t rop,
+ int16_t planemask /* ignored */)
+{
+ int width; /* add to get to same position in next line */
+
+ u_int32_t *psrcLine, *pdstLine;
+ /* pointers to line with current src and dst */
+ u_int32_t *psrc; /* pointer to current src longword */
+ u_int32_t *pdst; /* pointer to current dst longword */
+
+ /* following used for looping through a line */
+ u_int32_t startmask, endmask; /* masks for writing ends of dst */
+ int nlMiddle; /* whole longwords in dst */
+ int nl; /* temp copy of nlMiddle */
+ int xoffSrc; /* offset (>= 0, < 32) from which to
+ fetch whole longwords fetched in src */
+ int nstart; /* number of ragged bits at start of dst */
+ int nend; /* number of ragged bits at end of dst */
+ int srcStartOver; /* pulling nstart bits from src
+ overflows into the next word? */
+
+ width = ri->ri_stride / 4; /* convert to number in longword */
+
+ if (sy < dy) { /* start at last scanline of rectangle */
+ psrcLine = ((u_int32_t *)OMFB_FB_WADDR)
+ + ((sy + cy - 1) * width);
+ pdstLine = ((u_int32_t *)OMFB_FB_WADDR)
+ + ((dy + cy - 1) * width);
+ width = -width;
+ } else { /* start at first scanline */
+ psrcLine = ((u_int32_t *)OMFB_FB_WADDR) + (sy * width);
+ pdstLine = ((u_int32_t *)OMFB_FB_WADDR) + (dy * width);
+ }
+
+ /* x direction doesn't matter for < 1 longword */
+ if (cx <= 32) {
+ int srcBit, dstBit; /* bit offset of src and dst */
+
+ pdstLine += (dx >> 5);
+ psrcLine += (sx >> 5);
+ psrc = psrcLine;
+ pdst = pdstLine;
+
+ srcBit = sx & 0x1f;
+ dstBit = dx & 0x1f;
+
+ while (cy--) {
+ getandputrop(P0(psrc), srcBit, dstBit, cx, P0(pdst), rop);
+ getandputrop(P1(psrc), srcBit, dstBit, cx, P1(pdst), rop);
+ getandputrop(P2(psrc), srcBit, dstBit, cx, P2(pdst), rop);
+ getandputrop(P3(psrc), srcBit, dstBit, cx, P3(pdst), rop);
+ pdst += width;
+ psrc += width;
+ }
+ } else {
+ maskbits(dx, cx, startmask, endmask, nlMiddle);
+ if (startmask)
+ nstart = 32 - (dx & 0x1f);
+ else
+ nstart = 0;
+ if (endmask)
+ nend = (dx + cx) & 0x1f;
+ else
+ nend = 0;
+
+ xoffSrc = ((sx & 0x1f) + nstart) & 0x1f;
+ srcStartOver = ((sx & 0x1f) + nstart) > 31;
+
+ if (sx >= dx) { /* move left to right */
+ pdstLine += (dx >> 5);
+ psrcLine += (sx >> 5);
+
+ while (cy--) {
+ psrc = psrcLine;
+ pdst = pdstLine;
+
+ if (startmask) {
+ getandputrop(P0(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, P0(pdst), rop);
+ getandputrop(P1(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, P1(pdst), rop);
+ getandputrop(P2(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, P2(pdst), rop);
+ getandputrop(P3(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, P3(pdst), rop);
+ pdst++;
+ if (srcStartOver)
+ psrc++;
+ }
+
+ /* special case for aligned operations */
+ if (xoffSrc == 0) {
+ nl = nlMiddle;
+ while (nl--) {
+ if (rop == RR_CLEAR) {
+ *P0(pdst) = 0;
+ *P1(pdst) = 0;
+ *P2(pdst) = 0;
+ *P3(pdst) = 0;
+ } else {
+ *P0(pdst) = *P0(psrc);
+ *P1(pdst) = *P1(psrc);
+ *P2(pdst) = *P2(psrc);
+ *P3(pdst) = *P3(psrc);
+ }
+ psrc++;
+ pdst++;
+ }
+ } else {
+ nl = nlMiddle + 1;
+ while (--nl) {
+ if (rop == RR_CLEAR) {
+ *P0(pdst) = 0;
+ *P1(pdst) = 0;
+ *P2(pdst) = 0;
+ *P3(pdst) = 0;
+ } else {
+ getunalignedword(P0(psrc),
+ xoffSrc, *P0(pdst));
+ getunalignedword(P1(psrc),
+ xoffSrc, *P1(pdst));
+ getunalignedword(P2(psrc),
+ xoffSrc, *P2(pdst));
+ getunalignedword(P3(psrc),
+ xoffSrc, *P3(pdst));
+ }
+ pdst++;
+ psrc++;
+ }
+ }
+
+ if (endmask) {
+ getandputrop(P0(psrc), xoffSrc, 0, nend,
+ P0(pdst), rop);
+ getandputrop(P1(psrc), xoffSrc, 0, nend,
+ P1(pdst), rop);
+ getandputrop(P2(psrc), xoffSrc, 0, nend,
+ P2(pdst), rop);
+ getandputrop(P3(psrc), xoffSrc, 0, nend,
+ P3(pdst), rop);
+ }
+
+ pdstLine += width;
+ psrcLine += width;
+ }
+ } else { /* move right to left */
+ pdstLine += ((dx + cx) >> 5);
+ psrcLine += ((sx + cx) >> 5);
+ /*
+ * If fetch of last partial bits from source crosses
+ * a longword boundary, start at the previous longword
+ */
+ if (xoffSrc + nend >= 32)
+ --psrcLine;
+
+ while (cy--) {
+ psrc = psrcLine;
+ pdst = pdstLine;
+
+ if (endmask) {
+ getandputrop(P0(psrc), xoffSrc, 0, nend,
+ P0(pdst), rop);
+ getandputrop(P1(psrc), xoffSrc, 0, nend,
+ P1(pdst), rop);
+ getandputrop(P2(psrc), xoffSrc, 0, nend,
+ P2(pdst), rop);
+ getandputrop(P3(psrc), xoffSrc, 0, nend,
+ P3(pdst), rop);
+ }
+
+ nl = nlMiddle + 1;
+ while (--nl) {
+ --psrc;
+ --pdst;
+ if (rop == RR_CLEAR) {
+ *P0(pdst) = 0;
+ *P1(pdst) = 0;
+ *P2(pdst) = 0;
+ *P3(pdst) = 0;
+ } else {
+ getunalignedword(P0(psrc),
+ xoffSrc, *P0(pdst));
+ getunalignedword(P1(psrc),
+ xoffSrc, *P1(pdst));
+ getunalignedword(P2(psrc),
+ xoffSrc, *P2(pdst));
+ getunalignedword(P3(psrc),
+ xoffSrc, *P3(pdst));
+ }
}
if (startmask) {
if (srcStartOver)
--psrc;
--pdst;
- getandputrop(psrc, (sx & 0x1f),
- (dx & 0x1f), nstart, pdst, rop);
+ getandputrop(P0(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, P0(pdst), rop);
+ getandputrop(P1(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, P1(pdst), rop);
+ getandputrop(P2(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, P2(pdst), rop);
+ getandputrop(P3(psrc), (sx & 0x1f),
+ (dx & 0x1f), nstart, P3(pdst), rop);
}
pdstLine += width;
-/* $OpenBSD: pmap_table.c,v 1.9 2013/11/16 18:45:20 miod Exp $ */
+/* $OpenBSD: pmap_table.c,v 1.10 2014/01/02 15:30:34 aoyama Exp $ */
/*
* Mach Operating System
{ BMAP_BMSEL, PAGE_SIZE, RW, CI },
{ BMAP_BMP, BMAP_BMAP0 - BMAP_BMP, RW, CI, TRUE },
{ BMAP_BMAP0, BMAP_BMAP1 - BMAP_BMAP0, RW, CI, TRUE },
-#if 0 /* not until console or X11 needs them */
- { BMAP_BMAP1, BMAP_BMAP2 - BMAP_BMAP1, RW, CI },
- { BMAP_BMAP2, BMAP_BMAP3 - BMAP_BMAP2, RW, CI },
- { BMAP_BMAP3, BMAP_BMAP4 - BMAP_BMAP3, RW, CI },
- { BMAP_BMAP4, BMAP_BMAP5 - BMAP_BMAP4, RW, CI },
- { BMAP_BMAP5, BMAP_BMAP6 - BMAP_BMAP5, RW, CI },
- { BMAP_BMAP6, BMAP_BMAP7 - BMAP_BMAP6, RW, CI },
- { BMAP_BMAP7, BMAP_FN - BMAP_BMAP7, RW, CI },
-#else
- { BMAP_BMAP1, PAGE_SIZE, RW, CI },
- { BMAP_BMAP2, PAGE_SIZE, RW, CI },
- { BMAP_BMAP3, PAGE_SIZE, RW, CI },
- { BMAP_BMAP4, PAGE_SIZE, RW, CI },
- { BMAP_BMAP5, PAGE_SIZE, RW, CI },
- { BMAP_BMAP6, PAGE_SIZE, RW, CI },
- { BMAP_BMAP7, PAGE_SIZE, RW, CI },
-#endif
+ { BMAP_BMAP1, BMAP_BMAP2 - BMAP_BMAP1, RW, CI, TRUE },
+ { BMAP_BMAP2, BMAP_BMAP3 - BMAP_BMAP2, RW, CI, TRUE },
+ { BMAP_BMAP3, BMAP_BMAP4 - BMAP_BMAP3, RW, CI, TRUE },
+ { BMAP_BMAP4, BMAP_BMAP5 - BMAP_BMAP4, RW, CI, TRUE },
+ { BMAP_BMAP5, BMAP_BMAP6 - BMAP_BMAP5, RW, CI, TRUE },
+ { BMAP_BMAP6, BMAP_BMAP7 - BMAP_BMAP6, RW, CI, TRUE },
+ { BMAP_BMAP7, BMAP_FN - BMAP_BMAP7, RW, CI, TRUE },
{ BMAP_FN, PAGE_SIZE, RW, CI },
-#if 0 /* not until console or X11 needs them */
{ BMAP_FN0, PAGE_SIZE, RW, CI },
{ BMAP_FN1, PAGE_SIZE, RW, CI },
{ BMAP_FN2, PAGE_SIZE, RW, CI },
{ BMAP_FN5, PAGE_SIZE, RW, CI },
{ BMAP_FN6, PAGE_SIZE, RW, CI },
{ BMAP_FN7, PAGE_SIZE, RW, CI },
-#endif
{ BMAP_PALLET0, PAGE_SIZE, RW, CI },
{ BMAP_PALLET1, PAGE_SIZE, RW, CI },
{ BMAP_PALLET2, PAGE_SIZE, RW, CI },