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/fb/gfb.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 /*-
    2  * Copyright (c) 2001 Andrew Miklic
    3  * All rights reserved.
    4  *
    5  * Redistribution and use in source and binary forms, with or without
    6  * modification, are permitted provided that the following conditions
    7  * are met:
    8  * 1. Redistributions of source code must retain the above copyright
    9  *    notice, this list of conditions and the following disclaimer.
   10  * 2. Redistributions in binary form must reproduce the above copyright
   11  *    notice, this list of conditions and the following disclaimer in the
   12  *    documentation and/or other materials provided with the distribution.
   13  *
   14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
   15  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
   16  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
   17  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
   18  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
   19  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
   20  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
   21  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
   22  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
   23  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   24  * SUCH DAMAGE.
   25  */
   26 /*
   27  * Copyright (c) 1995, 1996 Carnegie-Mellon University.
   28  * All rights reserved.
   29  *
   30  * Author: Chris G. Demetriou
   31  * 
   32  * Permission to use, copy, modify and distribute this software and
   33  * its documentation is hereby granted, provided that both the copyright
   34  * notice and this permission notice appear in all copies of the
   35  * software, derivative works or modified versions, and any portions
   36  * thereof, and that both notices appear in supporting documentation.
   37  * 
   38  * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS" 
   39  * CONDITION.  CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND 
   40  * FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
   41  * 
   42  * Carnegie Mellon requests users of this software to return to
   43  *
   44  *  Software Distribution Coordinator  or  Software.Distribution@CS.CMU.EDU
   45  *  School of Computer Science
   46  *  Carnegie Mellon University
   47  *  Pittsburgh PA 15213-3890
   48  *
   49  * any improvements or extensions that they make and grant Carnegie the
   50  * rights to redistribute these changes.
   51  */
   52 
   53 #include <sys/cdefs.h>
   54 __FBSDID("$FreeBSD: releng/5.0/sys/dev/fb/gfb.c 94617 2002-04-13 22:34:16Z obrien $");
   55 
   56 #include <machine/stdarg.h>
   57 
   58 #include <sys/param.h>
   59 #include <sys/systm.h>
   60 #include <sys/kernel.h>
   61 #include <sys/conf.h>
   62 #include <sys/proc.h>
   63 #include <sys/fcntl.h>
   64 #include <sys/malloc.h>
   65 #include <sys/fbio.h>
   66 
   67 #include <vm/vm.h>
   68 #include <vm/vm_param.h>
   69 #include <vm/pmap.h>
   70 
   71 #include <machine/md_var.h>
   72 #include <machine/pc/bios.h>
   73 #include <machine/clock.h>
   74 #include <machine/bus_memio.h>
   75 #include <machine/bus.h>
   76 #include <machine/pc/vesa.h>
   77 #include <machine/resource.h>
   78 #include <machine/rpb.h>
   79 
   80 #include <sys/bus.h>
   81 #include <sys/rman.h>
   82 
   83 #include <pci/pcireg.h>
   84 #include <pci/pcivar.h>
   85 
   86 #include <dev/fb/fbreg.h>
   87 #include <dev/fb/gfb.h>
   88 #include <dev/gfb/gfb_pci.h>
   89 
   90 #include "opt_gfb.h"
   91 
   92 struct gfb_softc *gfb_device_softcs[2][MAX_NUM_GFB_CARDS] = {
   93         {
   94                 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
   95                 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
   96         },
   97         {
   98                 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
   99                 NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL
  100         },
  101 };
  102 
  103 /*
  104    The following 9 variables exist only because we need statically
  105    allocated structures very early in boot to support gfb_configure()...
  106 */
  107 struct gfb_softc console;
  108 video_adapter_t console_adp;
  109 struct gfb_conf console_gfbc;
  110 u_char console_palette_red[256];
  111 u_char console_palette_green[256];
  112 u_char console_palette_blue[256];
  113 u_char console_cursor_palette_red[3];
  114 u_char console_cursor_palette_green[3];
  115 u_char console_cursor_palette_blue[3];
  116 
  117 extern struct gfb_font bold8x16;
  118 
  119 /*****************************************************************************
  120  *
  121  * FB-generic functions
  122  *
  123  ****************************************************************************/
  124 
  125 int
  126 gfb_probe(int unit, video_adapter_t **adpp, void *arg, int flags)
  127 {
  128         int error;
  129 
  130         /* Assume the best... */
  131         error = 0;
  132 
  133         if((*adpp = vid_get_adapter(vid_find_adapter((char *)arg, unit))) == NULL)
  134                 error = ENODEV;
  135         else
  136                 (*adpp)->va_flags |= V_ADP_PROBED;
  137 
  138         return(error);
  139 }
  140 
  141 int
  142 gfb_init(int unit, video_adapter_t *adp, int flags)
  143 {
  144         struct gfb_softc *sc;
  145         struct gfb_conf *gfbc;
  146         int error;
  147 
  148         /* Assume the best... */
  149         error = 0;
  150 
  151         if(!init_done(adp)) {
  152                 sc = gfb_device_softcs[adp->va_model][unit];
  153                 gfbc = sc->gfbc;
  154 
  155                 /* Initialize the RAMDAC... */
  156                 (*gfbc->ramdac_init)(sc);
  157 
  158                 /* Initialize the palettes... */
  159                 (*gfbc->ramdac_load_palette)(sc->adp, &sc->gfbc->palette);
  160                 (*gfbc->ramdac_load_cursor_palette)(sc->adp,
  161                     &sc->gfbc->cursor_palette);
  162 
  163                 /* Prepare the default font... */
  164                 (*vidsw[adp->va_index]->load_font)(adp, 0, bold8x16.height,
  165                     bold8x16.data, 0, 256);
  166                 adp->va_info.vi_cwidth = gfbc->fonts[0].width;
  167                 adp->va_info.vi_cheight = gfbc->fonts[0].height;
  168 
  169                 /*
  170                    Normalize vi_width and vi_height to be in terms of
  171                    on-screen characters, rather than pixels (*_init()
  172                    leaves them in terms of pixels...
  173                 */
  174                 adp->va_info.vi_width /= adp->va_info.vi_cwidth;
  175                 adp->va_info.vi_height /= adp->va_info.vi_cheight;
  176 
  177                 /* Enable the default font... */
  178                 (*vidsw[adp->va_index]->show_font)(adp, 0);
  179 
  180                 /* Enable future font-loading... */
  181                 adp->va_flags |= V_ADP_FONT;
  182 
  183                 /* Flag this initialization for this adapter... */      
  184                 adp->va_flags |= V_ADP_INITIALIZED;
  185         }
  186         return(error);
  187 }
  188 
  189 int
  190 gfb_get_info(video_adapter_t *adp, int mode, video_info_t *info)
  191 {
  192         int error;
  193 
  194         /* Assume the best... */
  195         error = 0;
  196 
  197         /*
  198            The info for GFB adapters does not depend on its mode,
  199            so just copy it indiscriminantly (actually, we originally
  200            checked the mode, but the current fb framework is somewhat
  201            sloppily done in places, and assumes VGA in several places,
  202            which makes such checks always fail for such GFBs as TGA)...
  203         */
  204         bcopy(&adp->va_info, info, sizeof(video_info_t));
  205         return(error);
  206 }
  207 
  208 int
  209 gfb_set_mode(video_adapter_t *adp, int mode)
  210 {
  211 
  212         adp->va_mode = mode;
  213         return(0);
  214 }
  215 
  216 int
  217 gfb_save_font(video_adapter_t *adp, int page, int fontsize, u_char *data,
  218     int ch, int count)
  219 {
  220         struct gfb_softc *sc;
  221         int error;
  222         int i;
  223 
  224         error = 0;
  225         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  226 
  227         /* Check the font information... */
  228         if((sc->gfbc->fonts[page].height != fontsize) ||
  229            (sc->gfbc->fonts[page].width != 8))
  230                 error = EINVAL;
  231         else
  232 
  233                 /*
  234                    Copy the character pixel array from our
  235                    very own private cache...
  236                 */
  237                 for(i = ch; i < count * fontsize; i++)
  238                         data[i] = adp->va_little_bitian ?
  239                             BIT_REVERSE(sc->gfbc->fonts[page].data[i]) :
  240                             sc->gfbc->fonts[page].data[i];
  241 
  242         return(error);
  243 }
  244 
  245 int
  246 gfb_load_font(video_adapter_t *adp, int page, int fontsize, u_char *data,
  247     int ch, int count)
  248 {
  249         struct gfb_softc *sc;
  250         int error;
  251         int i;
  252 
  253         error = 0;
  254         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  255 
  256         /* Copy the character pixel array into our very own private cache... */
  257         for(i = ch; i < count * fontsize; i++)
  258                 sc->gfbc->fonts[page].data[i] = adp->va_little_bitian ?
  259                     BIT_REVERSE(data[i]) : data[i];
  260 
  261         /* Save the font information... */
  262         sc->gfbc->fonts[page].height = fontsize;
  263         sc->gfbc->fonts[page].width = 8;
  264 
  265         return(error);
  266 }
  267 
  268 int
  269 gfb_show_font(video_adapter_t *adp, int page)
  270 {
  271         struct gfb_softc *sc;
  272         int error;
  273 
  274         error = 0;
  275         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  276 
  277         /* Normalize adapter values... */
  278         adp->va_info.vi_height *= adp->va_info.vi_cheight;
  279         adp->va_info.vi_width *= adp->va_info.vi_cwidth;
  280 
  281         /* Set the current font pixels... */
  282         sc->gfbc->font = sc->gfbc->fonts[page].data;
  283 
  284         /* Set the current font width... */
  285         adp->va_info.vi_cwidth = sc->gfbc->fonts[page].width;
  286 
  287         /* Set the current font height... */
  288         adp->va_info.vi_cheight = sc->gfbc->fonts[page].height;
  289 
  290         /* Recompute adapter values... */
  291         adp->va_info.vi_height /= adp->va_info.vi_cheight;
  292         adp->va_info.vi_width /= adp->va_info.vi_cwidth;
  293 
  294         return(error);
  295 }
  296 
  297 int
  298 gfb_save_palette(video_adapter_t *adp, u_char *palette)
  299 {
  300         struct gfb_softc *sc;
  301         int error;
  302         int i;
  303 
  304         error = 0;
  305         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  306 
  307 #if 0
  308         /* If we have a RAMDAC-specific counterpart, use it... */
  309         if(sc->gfbc->ramdac_save_palette)
  310                 error = sc->gfbc->ramdac_save_palette(adp, &sc->gfbc->palette);
  311 
  312         else
  313                 /* Otherwise, use the built-in functionality... */
  314                 error = sc->gfbc->builtin_save_palette(adp, &sc->gfbc->palette);
  315 #endif
  316 
  317         for(i = 0; i < sc->gfbc->palette.count; i++) {
  318                 palette[(3 * i)] = sc->gfbc->palette.red[i];
  319                 palette[(3 * i) + 1] = sc->gfbc->palette.green[i];
  320                 palette[(3 * i) + 2] = sc->gfbc->palette.blue[i];
  321         }
  322         return(error);
  323 }
  324 
  325 int
  326 gfb_load_palette(video_adapter_t *adp, u_char *palette)
  327 {
  328         struct gfb_softc *sc;
  329         int error;
  330         int i;
  331 
  332         error = 0;
  333         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  334 
  335         for(i = 0; i < sc->gfbc->palette.count; i++) {
  336                 sc->gfbc->palette.red[i] = palette[(3 * i)];
  337                 sc->gfbc->palette.green[i] = palette[(3 * i) + 1];
  338                 sc->gfbc->palette.blue[i] = palette[(3 * i) + 2];
  339         }
  340 
  341         /* If we have a RAMDAC-specific counterpart, use it... */
  342         if(sc->gfbc->ramdac_load_palette)
  343                 error = sc->gfbc->ramdac_load_palette(adp, &sc->gfbc->palette);
  344         else
  345                 /* Otherwise, use the built-in functionality... */
  346                 error = sc->gfbc->builtin_load_palette(adp, &sc->gfbc->palette);
  347 
  348         return(error);
  349 }
  350 
  351 int
  352 gfb_set_border(video_adapter_t *adp, int color)
  353 {
  354 
  355         return(ENODEV);
  356 }
  357 
  358 int
  359 gfb_save_state(video_adapter_t *adp, void *p, size_t size)
  360 {
  361         int i;
  362         u_int32_t *regs;
  363 
  364         regs = (u_int32_t *)p;
  365         regs[0] = size;
  366         for(i = 1; i <= size; i++)
  367                 regs[i] = READ_GFB_REGISTER(adp, i);
  368         return(0);
  369 }
  370 
  371 int
  372 gfb_load_state(video_adapter_t *adp, void *p)
  373 {
  374         size_t size;
  375         int i;
  376         u_int32_t *regs;
  377 
  378         regs = (u_int32_t *)p;
  379         size = regs[0];
  380         for(i = 1; i <= size; i++)
  381                 WRITE_GFB_REGISTER(adp, i, regs[i]);
  382         return(0);
  383 }
  384 
  385 int
  386 gfb_set_win_org(video_adapter_t *adp, off_t offset)
  387 {
  388 
  389         adp->va_window_orig = offset;
  390         return(0);
  391 }
  392 
  393 int
  394 gfb_read_hw_cursor(video_adapter_t *adp, int *col, int *row)
  395 {
  396         struct gfb_softc *sc;
  397         int error;
  398 
  399         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  400 
  401         /* If we have a RAMDAC-specific counterpart, use it... */
  402         if(sc->gfbc->ramdac_read_hw_cursor)
  403                 error = sc->gfbc->ramdac_read_hw_cursor(adp, col, row);
  404         else
  405                 /* Otherwise, use the built-in functionality... */
  406                 error = sc->gfbc->builtin_read_hw_cursor(adp, col, row);
  407 
  408         return(error);
  409 }
  410 
  411 int
  412 gfb_set_hw_cursor(adp, col, row)
  413         video_adapter_t *adp;
  414         int col;
  415         int row;
  416 {
  417         int error;
  418         struct gfb_softc *sc;
  419 
  420         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  421 
  422         /* If we have a RAMDAC-specific counterpart, use it... */
  423         if(sc->gfbc->ramdac_set_hw_cursor)
  424                 error = sc->gfbc->ramdac_set_hw_cursor(adp, col, row);
  425 
  426         /* Otherwise, use the built-in functionality... */
  427         else
  428                 error = sc->gfbc->builtin_set_hw_cursor(adp, col, row);
  429         return(error);
  430 }
  431 
  432 int
  433 gfb_set_hw_cursor_shape(video_adapter_t *adp, int base, int height,
  434     int cellsize, int blink)
  435 {
  436         struct gfb_softc *sc;
  437         int error;
  438 
  439         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  440 
  441         /* If we have a RAMDAC-specific counterpart, use it... */
  442         if(sc->gfbc->ramdac_set_hw_cursor_shape)
  443                 error = sc->gfbc->ramdac_set_hw_cursor_shape(adp, base, height,
  444                     cellsize, blink);
  445         else
  446                 /* Otherwise, use the built-in functionality... */
  447                 error = sc->gfbc->builtin_set_hw_cursor_shape(adp, base,
  448                     height, cellsize, blink);
  449 
  450         return(error);
  451 }
  452 
  453 int
  454 gfb_mmap(video_adapter_t *adp, vm_offset_t offset, int prot)
  455 {
  456         int error;
  457 
  458         if(offset > adp->va_window_size - PAGE_SIZE)
  459                 error = ENXIO;
  460 #ifdef __i386__
  461         error = i386_btop(adp->va_info.vi_window + offset);
  462 #elsif defined(__alpha__)
  463         error = alpha_btop(adp->va_info.vi_window + offset);
  464 #else
  465         error = ENXIO;
  466 #endif
  467         return(error);
  468 }
  469 
  470 int
  471 gfb_ioctl(video_adapter_t *adp, u_long cmd, caddr_t arg)
  472 {
  473         struct gfb_softc *sc;
  474         int error;
  475 
  476         error = 0;
  477         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  478 
  479         switch (cmd) {
  480         case FBIOPUTCMAP:
  481                 /* FALLTHROUGH */
  482         case FBIO_GETWINORG:
  483                 /* FALLTHROUGH */
  484         case FBIO_SETWINORG:
  485                 /* FALLTHROUGH */
  486         case FBIO_SETDISPSTART:
  487                 /* FALLTHROUGH */
  488         case FBIO_SETLINEWIDTH:
  489                 /* FALLTHROUGH */
  490         case FBIO_GETPALETTE:
  491                 /* FALLTHROUGH */
  492         case FBIOGTYPE:
  493                 /* FALLTHROUGH */
  494         case FBIOGETCMAP:
  495                 /* FALLTHROUGH */
  496         default:
  497                 error = fb_commonioctl(adp, cmd, arg); 
  498         }
  499         return(error);
  500 }
  501 
  502 int
  503 gfb_fill_rect(video_adapter_t *adp, int val, int x, int y, int cx, int cy)
  504 {
  505         int off;
  506 
  507         /*
  508            Just traverse the buffer, one pixel span at a time, setting
  509            each pixel to the block-color...
  510         */
  511         for(off = (x * y); off < ((x + cx) * (y + cy)); off++)
  512                 (*vidsw[adp->va_index]->putp)(adp, off, 0x000007ff, 0xffffffff,
  513                     sizeof(u_int32_t), 1, 0, 0);
  514 
  515         return(0);
  516 }
  517 
  518 int
  519 gfb_bitblt(video_adapter_t *adp, ...)
  520 {
  521         va_list args;
  522         vm_offset_t src, dst;
  523         int count, i;
  524         u_int32_t val;
  525 
  526         va_start(args, adp);
  527 
  528         src = (va_arg(args, vm_offset_t) + adp->va_window_orig) &
  529             0x0000000000fffff8;
  530         dst = (va_arg(args, vm_offset_t) + adp->va_window_orig) &
  531             0x0000000000fffff8;
  532         count = va_arg(args, int);
  533         for(i = 0; i < count; i++, src++, dst++) {
  534                 val = READ_GFB_BUFFER(adp, src);
  535                 WRITE_GFB_BUFFER(adp, dst, val);
  536         }
  537         va_end(args);
  538         return(0);
  539 }
  540 
  541 int
  542 /*gfb_clear(video_adapter_t *adp, int n)*/
  543 gfb_clear(video_adapter_t *adp)
  544 {
  545         int off;
  546 
  547 #if 0
  548         if(n == 0)
  549                 return(0);
  550 #endif
  551 
  552         /*
  553            Just traverse the buffer, one 2K-pixel span at a time, clearing
  554            each pixel...
  555         */
  556         /* for(off = 0; off < (n * adp->va_line_width); off += (2 KB)) */
  557         for(off = 0; off < adp->va_window_size; off++)
  558                 (*vidsw[adp->va_index]->putp)(adp, off, 0x000007ff, 0xffffffff,
  559                     sizeof(u_int32_t), 1, 0, 0);
  560 
  561         return(0);
  562 }
  563 
  564 int
  565 gfb_diag(video_adapter_t *adp, int level)
  566 {
  567         video_info_t info;
  568         struct gfb_softc *sc;
  569         int error;
  570 
  571         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  572 
  573         /* Just dump everything we know about the adapter to the screen... */
  574         fb_dump_adp_info(sc->driver_name, adp, level);
  575 
  576         /* Try to get the info on this adapter... */
  577         if(!(error = (*vidsw[adp->va_index]->get_info)(adp,
  578             adp->va_initial_mode, &info)))
  579                 /*
  580                    Just dump everything we know about the adapter's mode
  581                    to the screen...
  582                 */
  583                 fb_dump_mode_info(sc->driver_name, adp, &info, level);
  584 
  585         return(error);
  586 }
  587 
  588 int
  589 gfb_save_cursor_palette(video_adapter_t *adp, u_char *palette)
  590 {
  591         struct gfb_softc *sc;
  592         int error, i;
  593 
  594         error = 0;
  595         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  596 
  597 #if 0
  598         /* If we have a RAMDAC-specific counterpart, use it... */
  599         if(sc->gfbc->ramdac_save_cursor_palette)
  600                 error = sc->gfbc->ramdac_save_cursor_palette(adp,
  601                     &sc->gfbc->cursor_palette);
  602 
  603         else
  604                 /* Otherwise, use the built-in functionality... */
  605                 error = sc->gfbc->builtin_save_cursor_palette(adp,
  606                     &sc->gfbc->cursor_palette);
  607 #endif
  608 
  609         for(i = 0; i < sc->gfbc->cursor_palette.count; i++) {
  610                 palette[(3 * i)] = sc->gfbc->cursor_palette.red[i];
  611                 palette[(3 * i) + 1] = sc->gfbc->cursor_palette.green[i];
  612                 palette[(3 * i) + 2] = sc->gfbc->cursor_palette.blue[i];
  613         }
  614         return(error);
  615 }
  616 
  617 int
  618 gfb_load_cursor_palette(video_adapter_t *adp, u_char *palette)
  619 {
  620         struct gfb_softc *sc;
  621         int error, i;
  622 
  623         error = 0;
  624         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  625 
  626         for(i = 0; i < sc->gfbc->cursor_palette.count; i++) {
  627                 sc->gfbc->cursor_palette.red[i] = palette[(3 * i)];
  628                 sc->gfbc->cursor_palette.green[i] = palette[(3 * i) + 1];
  629                 sc->gfbc->cursor_palette.blue[i] = palette[(3 * i) + 2];
  630         }
  631 
  632         /* If we have a RAMDAC-specific counterpart, use it... */
  633         if(sc->gfbc->ramdac_load_cursor_palette)
  634                 error = sc->gfbc->ramdac_load_cursor_palette(adp,
  635                     &sc->gfbc->cursor_palette);
  636         else
  637                 /* Otherwise, use the built-in functionality... */
  638                 error = sc->gfbc->builtin_load_cursor_palette(adp,
  639                     &sc->gfbc->cursor_palette);
  640 
  641         return(error);
  642 }
  643 
  644 int
  645 gfb_copy(video_adapter_t *adp, vm_offset_t src, vm_offset_t dst, int n)
  646 {
  647         int error, num_pixels;
  648 
  649         if(n == 0)
  650                 return(0);
  651         num_pixels = adp->va_info.vi_cheight * adp->va_line_width;
  652         error = (*vidsw[adp->va_index]->bitblt)(adp, src * num_pixels,
  653             dst * num_pixels, n * num_pixels);
  654         return(error);
  655 }
  656 
  657 int
  658 gfb_putp(video_adapter_t *adp, vm_offset_t off, u_int32_t p, u_int32_t a,
  659     int size, int bpp, int bit_ltor, int byte_ltor)
  660 {
  661         int i, j, k, num_shifts;
  662         u_int32_t _p, val[32];
  663 
  664         if(bpp < 1)
  665                 return(-1);
  666 
  667         /*
  668             If we don't display bits right-to-left (little-bitian?),
  669             then perform a bit-swap on p...
  670         */
  671         if(bit_ltor) {
  672                 num_shifts = 8 * size;
  673                 for(i = 0, _p = 0; i < num_shifts; i++, p >>= 1) {
  674                         _p <<= 1;
  675                         _p |= (p & 0x00000001);
  676                 }
  677         } else
  678                 _p = p;
  679 
  680         switch(bpp) {
  681         /* Accelerate the simplest cases... */
  682         case 1:
  683                 if((a & 0x00000001) == 0)
  684                         val[0] = 0;
  685                 else if(size <= 0)
  686                         val[0] = 0;
  687                 else if(size == 1)
  688                         val[0] = _p & 0x000000ff;
  689                 else if(size == 2)
  690                         val[0] = _p & 0x0000ffff;
  691                 else if(size == 3)
  692                         val[0] = _p & 0x00ffffff;
  693                 else if(size == 4)
  694                         val[0] = _p & 0xffffffff;
  695                 break;
  696 
  697         /* Only do the following if we are not a simple case... */
  698         case 8:
  699                 if(size > 0) {
  700                         a &= 0x000000ff;
  701                         val[0] = 0;
  702                         if(_p & 0x00000001) val[0] |= (a);
  703                         if(_p & 0x00000002) val[0] |= (a << 8);
  704                         if(_p & 0x00000004) val[0] |= (a << 16);
  705                         if(_p & 0x00000008) val[0] |= (a << 24);
  706                         val[1] = 0;
  707                         if(_p & 0x00000010) val[1] |= (a);
  708                         if(_p & 0x00000020) val[1] |= (a << 8);
  709                         if(_p & 0x00000040) val[1] |= (a << 16);
  710                         if(_p & 0x00000080) val[1] |= (a << 24);
  711                 }
  712                 if(size > 1) {
  713                         val[2] = 0;
  714                         if(_p & 0x00000100) val[2] |= (a);
  715                         if(_p & 0x00000200) val[2] |= (a << 8);
  716                         if(_p & 0x00000400) val[2] |= (a << 16);
  717                         if(_p & 0x00000800) val[2] |= (a << 24);
  718                         val[3] = 0;
  719                         if(_p & 0x00001000) val[3] |= (a);
  720                         if(_p & 0x00002000) val[3] |= (a << 8);
  721                         if(_p & 0x00004000) val[3] |= (a << 16);
  722                         if(_p & 0x00008000) val[3] |= (a << 24);
  723                 }       
  724                 if(size > 2) {
  725                         val[4] = 0;
  726                         if(_p & 0x00010000) val[4] |= (a);
  727                         if(_p & 0x00020000) val[4] |= (a << 8);
  728                         if(_p & 0x00040000) val[4] |= (a << 16);
  729                         if(_p & 0x00080000) val[4] |= (a << 24);
  730                         val[5] = 0;
  731                         if(_p & 0x00100000) val[5] |= (a);
  732                         if(_p & 0x00200000) val[5] |= (a << 8);
  733                         if(_p & 0x00400000) val[5] |= (a << 16);
  734                         if(_p & 0x00800080) val[5] |= (a << 24);
  735                 }
  736                 if(size > 3) {
  737                         val[6] = 0;
  738                         if(_p & 0x01000000) val[6] |= (a);
  739                         if(_p & 0x02000000) val[6] |= (a << 8);
  740                         if(_p & 0x04000000) val[6] |= (a << 16);
  741                         if(_p & 0x08000000) val[6] |= (a << 24);
  742                         val[7] = 0;
  743                         if(_p & 0x10000000) val[7] |= (a);
  744                         if(_p & 0x20000000) val[7] |= (a << 8);
  745                         if(_p & 0x40000000) val[7] |= (a << 16);
  746                         if(_p & 0x80000000) val[7] |= (a << 24);
  747                 }
  748                 break;
  749         case 16:
  750                 if(size > 0) {
  751                         a &= 0x0000ffff;
  752                         if(_p & 0x00000001) val[0] |= (a);
  753                         if(_p & 0x00000002) val[0] |= (a << 16);
  754                         if(_p & 0x00000004) val[1] |= (a);
  755                         if(_p & 0x00000008) val[1] |= (a << 16);
  756                         if(_p & 0x00000010) val[2] |= (a);
  757                         if(_p & 0x00000020) val[2] |= (a << 16);
  758                         if(_p & 0x00000040) val[3] |= (a);
  759                         if(_p & 0x00000080) val[3] |= (a << 16);
  760                 }
  761                 if(size > 1) {
  762                         if(_p & 0x00000100) val[4] |= (a);
  763                         if(_p & 0x00000200) val[4] |= (a << 16);
  764                         if(_p & 0x00000400) val[5] |= (a);
  765                         if(_p & 0x00000800) val[5] |= (a << 16);
  766                         if(_p & 0x00001000) val[6] |= (a);
  767                         if(_p & 0x00002000) val[6] |= (a << 16);
  768                         if(_p & 0x00004000) val[7] |= (a);
  769                         if(_p & 0x00008000) val[7] |= (a << 16);
  770                 }
  771                 if(size > 2) {
  772                         if(_p & 0x00010000) val[8] |= (a);
  773                         if(_p & 0x00020000) val[8] |= (a << 16);
  774                         if(_p & 0x00040000) val[9] |= (a);
  775                         if(_p & 0x00080000) val[9] |= (a << 16);
  776                         if(_p & 0x00100000) val[10] |= (a);
  777                         if(_p & 0x00200000) val[10] |= (a << 16);
  778                         if(_p & 0x00400000) val[11] |= (a);
  779                         if(_p & 0x00800000) val[11] |= (a << 16);
  780                 }
  781                 if(size > 3) {
  782                         if(_p & 0x01000000) val[12] |= (a);
  783                         if(_p & 0x02000000) val[12] |= (a << 16);
  784                         if(_p & 0x04000000) val[13] |= (a);
  785                         if(_p & 0x08000000) val[13] |= (a << 16);
  786                         if(_p & 0x10000000) val[14] |= (a);
  787                         if(_p & 0x20000000) val[14] |= (a << 16);
  788                         if(_p & 0x40000000) val[15] |= (a);
  789                         if(_p & 0x80000000) val[15] |= (a << 16);
  790                 }
  791                 break;
  792         case 32:
  793                 if(size > 0) {
  794                         a &= 0xffffffff;
  795                         if(_p & 0x00000001) val[0] = (a);
  796                         if(_p & 0x00000002) val[1] = (a);
  797                         if(_p & 0x00000004) val[2] = (a);
  798                         if(_p & 0x00000008) val[3] = (a);
  799                         if(_p & 0x00000010) val[4] = (a);
  800                         if(_p & 0x00000020) val[5] = (a);
  801                         if(_p & 0x00000040) val[6] = (a);
  802                         if(_p & 0x00000080) val[7] = (a);
  803                 }
  804                 if(size > 1) {
  805                         if(_p & 0x00000100) val[8] = (a);
  806                         if(_p & 0x00000200) val[9] = (a);
  807                         if(_p & 0x00000400) val[10] = (a);
  808                         if(_p & 0x00000800) val[11] = (a);
  809                         if(_p & 0x00001000) val[12] = (a);
  810                         if(_p & 0x00002000) val[13] = (a);
  811                         if(_p & 0x00004000) val[14] = (a);
  812                         if(_p & 0x00008000) val[15] = (a);
  813                 }
  814                 if(size > 2) {
  815                         if(_p & 0x00010000) val[16] = (a);
  816                         if(_p & 0x00020000) val[17] = (a);
  817                         if(_p & 0x00040000) val[18] = (a);
  818                         if(_p & 0x00080000) val[19] = (a);
  819                         if(_p & 0x00100000) val[20] = (a);
  820                         if(_p & 0x00200000) val[21] = (a);
  821                         if(_p & 0x00400000) val[22] = (a);
  822                         if(_p & 0x00800000) val[23] = (a);
  823                 }
  824                 if(size > 3) {
  825                         if(_p & 0x01000000) val[24] = (a);
  826                         if(_p & 0x02000000) val[25] = (a);
  827                         if(_p & 0x04000000) val[26] = (a);
  828                         if(_p & 0x08000000) val[27] = (a);
  829                         if(_p & 0x10000000) val[28] = (a);
  830                         if(_p & 0x20000000) val[29] = (a);
  831                         if(_p & 0x40000000) val[30] = (a);
  832                         if(_p & 0x80000000) val[31] = (a);
  833                 }
  834                 break;
  835         default:
  836                 break;
  837         }
  838         j = (bpp == 1) ? 1 : bpp * size / sizeof(u_int32_t);
  839 
  840         /*
  841             If we don't display bytes right-to-left (little-endian),
  842             then perform a byte-swap on p (we don't have to swap if
  843             bpp == 1 and val[0] == 0)...
  844         */
  845         if((byte_ltor) && (j > 1) && (val[j] != 0)) {
  846                 for(i = 0; i < (j - i); i++) {
  847                         _p = val[j - i];
  848                         val[j - i] = val[i];
  849                         val[i] = _p;
  850                 }
  851                 for(i = 0; i < j; i++) {
  852                         _p = val[i];
  853                         for(k = 0, val[i] = 0; k < sizeof(u_int32_t);
  854                             k++, _p >>= 8) {
  855                                 val[i] <<= 8;
  856                                 val[i] |= (_p & 0xff);
  857                         }
  858                 }
  859         }
  860 
  861         for(i = 0; i < j; i++) {
  862                 /* Write the pixel-row... */
  863                 WRITE_GFB_BUFFER(adp, (off + i), val[i]);
  864         }
  865         return(0);
  866 }
  867 
  868 int
  869 gfb_putc(video_adapter_t *adp, vm_offset_t off, u_int8_t c, u_int8_t a)
  870 {
  871         vm_offset_t poff;
  872         struct gfb_softc *sc;
  873         int i, pixel_size;
  874         u_int row, col;
  875         u_int8_t *pixel;
  876 
  877         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  878         pixel_size = adp->va_info.vi_depth / 8;
  879 
  880         /* Get the start of the array of pixels rows for this character... */
  881         pixel = sc->gfbc->font + (c * adp->va_info.vi_cheight);
  882 
  883         /* Calculate the new cursor position... */
  884         row = off / adp->va_info.vi_width;
  885         col = off % adp->va_info.vi_width;
  886 
  887         /* Iterate over all the pixel rows for this character... */
  888         for(i = 0; i < adp->va_info.vi_cheight; i++) {
  889                 /* Get the address of the character's pixel-row... */
  890                 poff = ((col * adp->va_info.vi_cwidth * pixel_size) +
  891                     (((row * adp->va_info.vi_cheight) + i) *
  892                     adp->va_line_width)) / sizeof(u_int32_t);
  893 
  894                 /* Now display the current pixel row... */
  895                 (*vidsw[adp->va_index]->putp)(adp, poff, pixel[i], a,
  896                     sizeof(u_int8_t), 1, 1, 0);
  897         }
  898         return(0);
  899 }
  900 
  901 int
  902 gfb_puts(video_adapter_t *adp, vm_offset_t off, u_int16_t *s, int len)
  903 {
  904         struct gfb_softc *sc;
  905         int i;
  906 
  907         sc = gfb_device_softcs[adp->va_model][adp->va_unit];
  908 
  909         /* If the string in empty, just return now... */
  910         if(len == 0)
  911                 return(0);
  912 
  913         for(i = 0; i < len; i++)
  914                 (*vidsw[adp->va_index]->putc)(adp, off + i, s[i] & 0x00ff,
  915                     (s[i] & 0xff00) >> 8);
  916 
  917         return(0);
  918 }
  919 
  920 int
  921 gfb_putm(video_adapter_t *adp, int x, int y, u_int8_t *pixel_image,
  922     u_int32_t pixel_mask, int size)
  923 {
  924         vm_offset_t poff;
  925         int i, pixel_size;
  926 
  927         pixel_size = adp->va_info.vi_depth / 8;
  928 
  929         /* Iterate over all the pixel rows for the mouse pointer... */
  930         for(i = 0; i < size; i++) {
  931                 /* Get the address of the mouse pointer's pixel-row... */
  932                 poff = ((x * pixel_size) + ((y + i) * adp->va_line_width)) /
  933                     sizeof(u_int32_t);
  934                 /* Now display the current pixel-row... */
  935                 (*vidsw[adp->va_index]->putp)(adp, poff, pixel_image[i],
  936                     pixel_mask, sizeof(u_int8_t), 1, 1, 0);
  937         }
  938 
  939         return(0);
  940 }
  941 
  942 int
  943 gfb_error(void)
  944 {
  945 
  946         return(0);
  947 }

Cache object: 624e09212d12d9abf6745434c859da92


[ 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.