The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/dev/ic/pcdisplay_subr.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /* $NetBSD: pcdisplay_subr.c,v 1.34 2007/10/19 11:59:58 ad Exp $ */
    2 
    3 /*
    4  * Copyright (c) 1995, 1996 Carnegie-Mellon University.
    5  * All rights reserved.
    6  *
    7  * Author: Chris G. Demetriou
    8  *
    9  * Permission to use, copy, modify and distribute this software and
   10  * its documentation is hereby granted, provided that both the copyright
   11  * notice and this permission notice appear in all copies of the
   12  * software, derivative works or modified versions, and any portions
   13  * thereof, and that both notices appear in supporting documentation.
   14  *
   15  * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
   16  * CONDITION.  CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND
   17  * FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
   18  *
   19  * Carnegie Mellon requests users of this software to return to
   20  *
   21  *  Software Distribution Coordinator  or  Software.Distribution@CS.CMU.EDU
   22  *  School of Computer Science
   23  *  Carnegie Mellon University
   24  *  Pittsburgh PA 15213-3890
   25  *
   26  * any improvements or extensions that they make and grant Carnegie the
   27  * rights to redistribute these changes.
   28  */
   29 
   30 #include <sys/cdefs.h>
   31 __KERNEL_RCSID(0, "$NetBSD: pcdisplay_subr.c,v 1.34 2007/10/19 11:59:58 ad Exp $");
   32 
   33 #include "opt_wsmsgattrs.h" /* for WSDISPLAY_CUSTOM_OUTPUT */
   34 
   35 #include <sys/param.h>
   36 #include <sys/systm.h>
   37 #include <sys/device.h>
   38 #include <sys/bus.h>
   39 
   40 #include <dev/ic/mc6845reg.h>
   41 #include <dev/ic/pcdisplayvar.h>
   42 #include <dev/wscons/wsconsio.h>
   43 
   44 #include <dev/wscons/wsdisplayvar.h>
   45 
   46 void
   47 pcdisplay_cursor_init(struct pcdisplayscreen *scr, int existing)
   48 {
   49 #ifdef PCDISPLAY_SOFTCURSOR
   50         bus_space_tag_t memt;
   51         bus_space_handle_t memh;
   52         int off;
   53 
   54         pcdisplay_6845_write(scr->hdl, curstart, 0x10);
   55         pcdisplay_6845_write(scr->hdl, curend, 0x10);
   56 
   57         if (existing) {
   58                 /*
   59                  * This is the first screen. At this point, scr->mem is NULL
   60                  * (no backing store), so we can't use pcdisplay_cursor() to
   61                  * do this.
   62                  */
   63                 memt = scr->hdl->ph_memt;
   64                 memh = scr->hdl->ph_memh;
   65                 off = (scr->cursorrow * scr->type->ncols + scr->cursorcol) * 2
   66                     + scr->dispoffset;
   67 
   68                 scr->cursortmp = bus_space_read_2(memt, memh, off);
   69                 bus_space_write_2(memt, memh, off, scr->cursortmp ^ 0x7700);
   70         } else
   71                 scr->cursortmp = 0;
   72 #else
   73         /*
   74          * Firmware might not have initialized the cursor shape.  Make
   75          * sure there's something we can see.
   76          * Don't touch the hardware if this is not the first screen.
   77          */
   78         if (existing) {
   79                 pcdisplay_6845_write(scr->hdl, curstart,
   80                                      scr->type->fontheight - 2);
   81                 pcdisplay_6845_write(scr->hdl, curend,
   82                                      scr->type->fontheight - 1);
   83         }
   84 #endif
   85         scr->cursoron = 1;
   86 }
   87 
   88 void
   89 pcdisplay_cursor(void *id, int on, int row, int col)
   90 {
   91 #ifdef PCDISPLAY_SOFTCURSOR
   92         struct pcdisplayscreen *scr = id;
   93         bus_space_tag_t memt = scr->hdl->ph_memt;
   94         bus_space_handle_t memh = scr->hdl->ph_memh;
   95         int off;
   96 
   97         /* Remove old cursor image */
   98         if (scr->cursoron) {
   99                 off = scr->cursorrow * scr->type->ncols + scr->cursorcol;
  100                 if (scr->active)
  101                         bus_space_write_2(memt, memh, scr->dispoffset + off * 2,
  102                             scr->cursortmp);
  103                 else
  104                         scr->mem[off] = scr->cursortmp;
  105         }
  106 
  107         scr->cursorrow = row;
  108         scr->cursorcol = col;
  109 
  110         if ((scr->cursoron = on) == 0)
  111                 return;
  112 
  113         off = (scr->cursorrow * scr->type->ncols + scr->cursorcol);
  114         if (scr->active) {
  115                 off = off * 2 + scr->dispoffset;
  116                 scr->cursortmp = bus_space_read_2(memt, memh, off);
  117                 bus_space_write_2(memt, memh, off, scr->cursortmp ^ 0x7700);
  118         } else {
  119                 scr->cursortmp = scr->mem[off];
  120                 scr->mem[off] = scr->cursortmp ^ 0x7700;
  121         }
  122 #else   /* PCDISPLAY_SOFTCURSOR */
  123         struct pcdisplayscreen *scr = id;
  124         int pos;
  125 
  126         scr->cursorrow = row;
  127         scr->cursorcol = col;
  128         scr->cursoron = on;
  129 
  130         if (scr->active) {
  131                 if (!on)
  132                         pos = 0x3fff;
  133                 else
  134                         pos = scr->dispoffset / 2
  135                                 + row * scr->type->ncols + col;
  136 
  137                 pcdisplay_6845_write(scr->hdl, cursorh, pos >> 8);
  138                 pcdisplay_6845_write(scr->hdl, cursorl, pos);
  139         }
  140 #endif  /* PCDISPLAY_SOFTCURSOR */
  141 }
  142 
  143 #if 0
  144 unsigned int
  145 pcdisplay_mapchar_simple(void *id, int uni)
  146 {
  147         if (uni < 128)
  148                 return (uni);
  149 
  150         return (1); /* XXX ??? smiley */
  151 }
  152 #endif
  153 
  154 void
  155 pcdisplay_putchar(void *id, int row, int col, unsigned int c, long attr)
  156 {
  157         struct pcdisplayscreen *scr = id;
  158         bus_space_tag_t memt = scr->hdl->ph_memt;
  159         bus_space_handle_t memh = scr->hdl->ph_memh;
  160         size_t off;
  161 
  162         off = row * scr->type->ncols + col;
  163 
  164         /* check for bogus row and column sizes */
  165         if (__predict_false(off >= (scr->type->ncols * scr->type->nrows)))
  166                 return;
  167 
  168         if (scr->active)
  169                 bus_space_write_2(memt, memh, scr->dispoffset + off * 2,
  170                                   c | (attr << 8));
  171         else
  172                 scr->mem[off] = c | (attr << 8);
  173 
  174         scr->visibleoffset = scr->dispoffset;
  175 }
  176 
  177 void
  178 pcdisplay_copycols(void *id, int row, int srccol, int dstcol, int ncols)
  179 {
  180         struct pcdisplayscreen *scr = id;
  181         bus_space_tag_t memt = scr->hdl->ph_memt;
  182         bus_space_handle_t memh = scr->hdl->ph_memh;
  183         bus_size_t srcoff, dstoff;
  184 
  185         srcoff = dstoff = row * scr->type->ncols;
  186         srcoff += srccol;
  187         dstoff += dstcol;
  188 
  189         if (scr->active)
  190                 bus_space_copy_region_2(memt, memh,
  191                                         scr->dispoffset + srcoff * 2,
  192                                         memh, scr->dispoffset + dstoff * 2,
  193                                         ncols);
  194         else
  195                 memcpy(&scr->mem[dstoff], &scr->mem[srcoff], ncols * 2);
  196 }
  197 
  198 void
  199 pcdisplay_erasecols(void *id, int row, int startcol, int ncols, long fillattr)
  200 {
  201         struct pcdisplayscreen *scr = id;
  202         bus_space_tag_t memt = scr->hdl->ph_memt;
  203         bus_space_handle_t memh = scr->hdl->ph_memh;
  204         bus_size_t off;
  205         u_int16_t val;
  206         int i;
  207 
  208         off = row * scr->type->ncols + startcol;
  209 
  210         val = (fillattr << 8) | ' ';
  211 
  212         if (scr->active)
  213                 bus_space_set_region_2(memt, memh, scr->dispoffset + off * 2,
  214                                        val, ncols);
  215         else
  216                 for (i = 0; i < ncols; i++)
  217                         scr->mem[off + i] = val;
  218 }
  219 
  220 void
  221 pcdisplay_copyrows(void *id, int srcrow, int dstrow, int nrows)
  222 {
  223         struct pcdisplayscreen *scr = id;
  224         bus_space_tag_t memt = scr->hdl->ph_memt;
  225         bus_space_handle_t memh = scr->hdl->ph_memh;
  226         int ncols = scr->type->ncols;
  227         bus_size_t srcoff, dstoff;
  228 
  229         srcoff = srcrow * ncols + 0;
  230         dstoff = dstrow * ncols + 0;
  231 
  232         if (scr->active)
  233                 bus_space_copy_region_2(memt, memh,
  234                                         scr->dispoffset + srcoff * 2,
  235                                         memh, scr->dispoffset + dstoff * 2,
  236                                         nrows * ncols);
  237         else
  238                 memcpy(&scr->mem[dstoff], &scr->mem[srcoff],
  239                       nrows * ncols * 2);
  240 }
  241 
  242 void
  243 pcdisplay_eraserows(void *id, int startrow, int nrows, long fillattr)
  244 {
  245         struct pcdisplayscreen *scr = id;
  246         bus_space_tag_t memt = scr->hdl->ph_memt;
  247         bus_space_handle_t memh = scr->hdl->ph_memh;
  248         bus_size_t off, count;
  249         u_int16_t val;
  250         u_int i;
  251 
  252         off = startrow * scr->type->ncols;
  253         count = nrows * scr->type->ncols;
  254 
  255         val = (fillattr << 8) | ' ';
  256 
  257         if (scr->active)
  258                 bus_space_set_region_2(memt, memh, scr->dispoffset + off * 2,
  259                                        val, count);
  260         else
  261                 for (i = 0; i < count; i++)
  262                         scr->mem[off + i] = val;
  263 }
  264 
  265 #ifdef WSDISPLAY_CUSTOM_OUTPUT
  266 void
  267 pcdisplay_replaceattr(void *id, long oldattr, long newattr)
  268 {
  269         struct pcdisplayscreen *scr = id;
  270         bus_space_tag_t memt = scr->hdl->ph_memt;
  271         bus_space_handle_t memh = scr->hdl->ph_memh;
  272         int off;
  273         uint16_t chardata;
  274 
  275         if (scr->active)
  276                 for (off = 0; off < scr->type->nrows * scr->type->ncols;
  277                      off++) {
  278                         chardata = bus_space_read_2(memt, memh,
  279                                                     scr->dispoffset + off * 2);
  280                         if ((long)(chardata >> 8) == oldattr)
  281                                 bus_space_write_2(memt, memh,
  282                                                   scr->dispoffset + off * 2,
  283                                                   ((u_int16_t)(newattr << 8)) |
  284                                                   (chardata & 0x00FF));
  285                 }
  286         else
  287                 for (off = 0; off < scr->type->nrows * scr->type->ncols;
  288                      off++) {
  289                         chardata = scr->mem[off];
  290                         if ((long)(chardata >> 8) == oldattr)
  291                                 scr->mem[off] = ((u_int16_t)(newattr << 8)) |
  292                                                 (chardata & 0x00FF);
  293                 }
  294 }
  295 #endif /* WSDISPLAY_CUSTOM_OUTPUT */
  296 
  297 int
  298 pcdisplay_getwschar(struct pcdisplayscreen *scr, struct wsdisplay_char *wschar)
  299 {
  300         size_t off;
  301         uint16_t chardata;
  302         uint8_t attrbyte;
  303 
  304         KASSERT(scr != NULL && wschar != NULL);
  305 
  306         off = wschar->row * scr->type->ncols + wschar->col;
  307         if (off >= scr->type->ncols * scr->type->nrows)
  308                 return -1;
  309 
  310         if (scr->active)
  311                 chardata = bus_space_read_2(scr->hdl->ph_memt,
  312                     scr->hdl->ph_memh, scr->dispoffset + off * 2);
  313         else
  314                 chardata = scr->mem[off];
  315 
  316         wschar->letter = (chardata & 0x00FF);
  317         wschar->flags = 0;
  318         attrbyte = (chardata & 0xFF00) >> 8;
  319         if ((attrbyte & 0x08)) wschar->flags |= WSDISPLAY_CHAR_BRIGHT;
  320         if ((attrbyte & 0x80)) wschar->flags |= WSDISPLAY_CHAR_BLINK;
  321         wschar->foreground = attrbyte & 0x07;
  322         wschar->background = (attrbyte >> 4) & 0x07;
  323 
  324         return 0;
  325 }
  326 
  327 int
  328 pcdisplay_putwschar(struct pcdisplayscreen *scr, struct wsdisplay_char *wschar)
  329 {
  330         size_t off;
  331         uint16_t chardata;
  332         uint8_t attrbyte;
  333 
  334         KASSERT(scr != NULL && wschar != NULL);
  335 
  336         off = wschar->row * scr->type->ncols + wschar->col;
  337         if (off >= (scr->type->ncols * scr->type->nrows))
  338                 return -1;
  339 
  340         attrbyte = wschar->background & 0x07;
  341         if (wschar->flags & WSDISPLAY_CHAR_BLINK) attrbyte |= 0x08;
  342         attrbyte <<= 4;
  343         attrbyte |= wschar->foreground & 0x07;
  344         if (wschar->flags & WSDISPLAY_CHAR_BRIGHT) attrbyte |= 0x08;
  345         chardata = (attrbyte << 8) | wschar->letter;
  346 
  347         if (scr->active)
  348                 bus_space_write_2(scr->hdl->ph_memt, scr->hdl->ph_memh,
  349                     scr->dispoffset + off * 2, chardata);
  350         else
  351                 scr->mem[off] = chardata;
  352 
  353         return 0;
  354 }

Cache object: d80611807b005146580f4ecaf119c7a1


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.