[BACK]Return to wsfont.c CVS log [TXT][DIR] Up to [local] / sys / dev / wsfont

Annotation of sys/dev/wsfont/wsfont.c, Revision 1.1.1.1

1.1       nbrk        1: /*     $OpenBSD: wsfont.c,v 1.20 2006/08/06 16:00:46 miod Exp $ */
                      2: /*     $NetBSD: wsfont.c,v 1.17 2001/02/07 13:59:24 ad Exp $   */
                      3:
                      4: /*-
                      5:  * Copyright (c) 1999 The NetBSD Foundation, Inc.
                      6:  * All rights reserved.
                      7:  *
                      8:  * This code is derived from software contributed to The NetBSD Foundation
                      9:  * by Andrew Doran.
                     10:  *
                     11:  * Redistribution and use in source and binary forms, with or without
                     12:  * modification, are permitted provided that the following conditions
                     13:  * are met:
                     14:  * 1. Redistributions of source code must retain the above copyright
                     15:  *    notice, this list of conditions and the following disclaimer.
                     16:  * 2. Redistributions in binary form must reproduce the above copyright
                     17:  *    notice, this list of conditions and the following disclaimer in the
                     18:  *    documentation and/or other materials provided with the distribution.
                     19:  * 3. All advertising materials mentioning features or use of this software
                     20:  *    must display the following acknowledgement:
                     21:  *     This product includes software developed by the NetBSD
                     22:  *     Foundation, Inc. and its contributors.
                     23:  * 4. Neither the name of The NetBSD Foundation nor the names of its
                     24:  *    contributors may be used to endorse or promote products derived
                     25:  *    from this software without specific prior written permission.
                     26:  *
                     27:  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
                     28:  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
                     29:  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
                     30:  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
                     31:  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
                     32:  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
                     33:  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
                     34:  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
                     35:  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
                     36:  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
                     37:  * POSSIBILITY OF SUCH DAMAGE.
                     38:  */
                     39:
                     40: #include <sys/types.h>
                     41: #include <sys/param.h>
                     42: #include <sys/systm.h>
                     43: #include <sys/time.h>
                     44: #include <sys/malloc.h>
                     45:
                     46: #include <dev/wscons/wsdisplayvar.h>
                     47: #include <dev/wscons/wsconsio.h>
                     48: #include <dev/wsfont/wsfont.h>
                     49:
                     50: #include "wsfont_glue.h"       /* NRASOPS_ROTATION */
                     51:
                     52: #undef HAVE_FONT
                     53:
                     54: #ifdef FONT_QVSS8x15
                     55: #define HAVE_FONT 1
                     56: #include <dev/wsfont/qvss8x15.h>
                     57: #endif
                     58:
                     59: #ifdef FONT_LUCIDA16x29
                     60: #define HAVE_FONT 1
                     61: #include <dev/wsfont/lucida16x29.h>
                     62: #endif
                     63:
                     64: #ifdef FONT_VT220L8x8
                     65: #define HAVE_FONT 1
                     66: #include <dev/wsfont/vt220l8x8.h>
                     67: #endif
                     68:
                     69: #ifdef FONT_VT220L8x10
                     70: #define HAVE_FONT 1
                     71: #include <dev/wsfont/vt220l8x10.h>
                     72: #endif
                     73:
                     74: #ifdef FONT_SONY8x16
                     75: #define HAVE_FONT 1
                     76: #include <dev/wsfont/sony8x16.h>
                     77: #endif
                     78:
                     79: #ifdef FONT_SONY12x24
                     80: #define HAVE_FONT 1
                     81: #include <dev/wsfont/sony12x24.h>
                     82: #endif
                     83:
                     84: #ifdef FONT_OMRON12x20
                     85: #define HAVE_FONT 1
                     86: #include <dev/wsfont/omron12x20.h>
                     87: #endif
                     88:
                     89: #ifdef FONT_BOLD8x16
                     90: #define HAVE_FONT 1
                     91: #include <dev/wsfont/bold8x16.h>
                     92: #endif
                     93:
                     94: #ifdef FONT_GALLANT12x22
                     95: #define HAVE_FONT 1
                     96: #endif
                     97:
                     98: #ifdef FONT_BOLD8x16_ISO1
                     99: #define HAVE_FONT 1
                    100: #endif
                    101:
                    102: /*
                    103:  * Make sure we always have at least one font.
                    104:  * Sparc, sparc64 always provide a 8x16 font and a larger 12x22 font.
                    105:  * Other platforms also provide both, but the 12x22 font is omitted if
                    106:  * option SMALL_KERNEL.
                    107:  */
                    108: #ifndef HAVE_FONT
                    109: #define HAVE_FONT 1
                    110:
                    111: #define        FONT_BOLD8x16_ISO1
                    112: #if defined(__sparc__) || defined(__sparc64__) || defined(luna88k) || !defined(SMALL_KERNEL)
                    113: #define        FONT_GALLANT12x22
                    114: #endif
                    115:
                    116: #endif /* HAVE_FONT */
                    117:
                    118: #ifdef FONT_BOLD8x16_ISO1
                    119: #include <dev/wsfont/bold8x16-iso1.h>
                    120: #endif
                    121:
                    122: #ifdef FONT_GALLANT12x22
                    123: #include <dev/wsfont/gallant12x22.h>
                    124: #endif
                    125:
                    126: /* Placeholder struct used for linked list */
                    127: struct font {
                    128:        struct  font *next;
                    129:        struct  font *prev;
                    130:        struct  wsdisplay_font *font;
                    131:        u_short lockcount;
                    132:        u_short cookie;
                    133:        u_short flg;
                    134: };
                    135:
                    136: /* Our list of built-in fonts */
                    137: static struct font *list, builtin_fonts[] = {
                    138: #ifdef FONT_BOLD8x16
                    139:        { NULL, NULL, &bold8x16, 0, 1, WSFONT_STATIC | WSFONT_BUILTIN  },
                    140: #endif
                    141: #ifdef FONT_BOLD8x16_ISO1
                    142:        { NULL, NULL, &bold8x16_iso1, 0, 2, WSFONT_STATIC | WSFONT_BUILTIN },
                    143: #endif
                    144: #ifdef FONT_COURIER11x18
                    145:        { NULL, NULL, &courier11x18, 0, 3, WSFONT_STATIC | WSFONT_BUILTIN },
                    146: #endif
                    147: #ifdef FONT_GALLANT12x22
                    148:        { NULL, NULL, &gallant12x22, 0, 4, WSFONT_STATIC | WSFONT_BUILTIN },
                    149: #endif
                    150: #ifdef FONT_LUCIDA16x29
                    151:        { NULL, NULL, &lucida16x29, 0, 5, WSFONT_STATIC | WSFONT_BUILTIN },
                    152: #endif
                    153: #ifdef FONT_QVSS8x15
                    154:        { NULL, NULL, &qvss8x15, 0, 6, WSFONT_STATIC | WSFONT_BUILTIN },
                    155: #endif
                    156: #ifdef FONT_VT220L8x8
                    157:        { NULL, NULL, &vt220l8x8, 0, 7, WSFONT_STATIC | WSFONT_BUILTIN },
                    158: #endif
                    159: #ifdef FONT_VT220L8x10
                    160:        { NULL, NULL, &vt220l8x10, 0, 8, WSFONT_STATIC | WSFONT_BUILTIN },
                    161: #endif
                    162: #ifdef FONT_SONY8x16
                    163:        { NULL, NULL, &sony8x16, 0, 9, WSFONT_STATIC | WSFONT_BUILTIN },
                    164: #endif
                    165: #ifdef FONT_SONY12x24
                    166:        { NULL, NULL, &sony12x24, 0, 10, WSFONT_STATIC | WSFONT_BUILTIN },
                    167: #endif
                    168: #ifdef FONT_OMRON12x20
                    169:        { NULL, NULL, &omron12x20, 0, 11, WSFONT_STATIC | WSFONT_BUILTIN },
                    170: #endif
                    171:        { NULL, NULL, NULL, 0 },
                    172: };
                    173:
                    174: #if !defined(SMALL_KERNEL) || defined(__alpha__)
                    175:
                    176: /* Reverse the bit order in a byte */
                    177: static const u_char reverse[256] = {
                    178:        0x00, 0x80, 0x40, 0xc0, 0x20, 0xa0, 0x60, 0xe0,
                    179:        0x10, 0x90, 0x50, 0xd0, 0x30, 0xb0, 0x70, 0xf0,
                    180:        0x08, 0x88, 0x48, 0xc8, 0x28, 0xa8, 0x68, 0xe8,
                    181:        0x18, 0x98, 0x58, 0xd8, 0x38, 0xb8, 0x78, 0xf8,
                    182:        0x04, 0x84, 0x44, 0xc4, 0x24, 0xa4, 0x64, 0xe4,
                    183:        0x14, 0x94, 0x54, 0xd4, 0x34, 0xb4, 0x74, 0xf4,
                    184:        0x0c, 0x8c, 0x4c, 0xcc, 0x2c, 0xac, 0x6c, 0xec,
                    185:        0x1c, 0x9c, 0x5c, 0xdc, 0x3c, 0xbc, 0x7c, 0xfc,
                    186:        0x02, 0x82, 0x42, 0xc2, 0x22, 0xa2, 0x62, 0xe2,
                    187:        0x12, 0x92, 0x52, 0xd2, 0x32, 0xb2, 0x72, 0xf2,
                    188:        0x0a, 0x8a, 0x4a, 0xca, 0x2a, 0xaa, 0x6a, 0xea,
                    189:        0x1a, 0x9a, 0x5a, 0xda, 0x3a, 0xba, 0x7a, 0xfa,
                    190:        0x06, 0x86, 0x46, 0xc6, 0x26, 0xa6, 0x66, 0xe6,
                    191:        0x16, 0x96, 0x56, 0xd6, 0x36, 0xb6, 0x76, 0xf6,
                    192:        0x0e, 0x8e, 0x4e, 0xce, 0x2e, 0xae, 0x6e, 0xee,
                    193:        0x1e, 0x9e, 0x5e, 0xde, 0x3e, 0xbe, 0x7e, 0xfe,
                    194:        0x01, 0x81, 0x41, 0xc1, 0x21, 0xa1, 0x61, 0xe1,
                    195:        0x11, 0x91, 0x51, 0xd1, 0x31, 0xb1, 0x71, 0xf1,
                    196:        0x09, 0x89, 0x49, 0xc9, 0x29, 0xa9, 0x69, 0xe9,
                    197:        0x19, 0x99, 0x59, 0xd9, 0x39, 0xb9, 0x79, 0xf9,
                    198:        0x05, 0x85, 0x45, 0xc5, 0x25, 0xa5, 0x65, 0xe5,
                    199:        0x15, 0x95, 0x55, 0xd5, 0x35, 0xb5, 0x75, 0xf5,
                    200:        0x0d, 0x8d, 0x4d, 0xcd, 0x2d, 0xad, 0x6d, 0xed,
                    201:        0x1d, 0x9d, 0x5d, 0xdd, 0x3d, 0xbd, 0x7d, 0xfd,
                    202:        0x03, 0x83, 0x43, 0xc3, 0x23, 0xa3, 0x63, 0xe3,
                    203:        0x13, 0x93, 0x53, 0xd3, 0x33, 0xb3, 0x73, 0xf3,
                    204:        0x0b, 0x8b, 0x4b, 0xcb, 0x2b, 0xab, 0x6b, 0xeb,
                    205:        0x1b, 0x9b, 0x5b, 0xdb, 0x3b, 0xbb, 0x7b, 0xfb,
                    206:        0x07, 0x87, 0x47, 0xc7, 0x27, 0xa7, 0x67, 0xe7,
                    207:        0x17, 0x97, 0x57, 0xd7, 0x37, 0xb7, 0x77, 0xf7,
                    208:        0x0f, 0x8f, 0x4f, 0xcf, 0x2f, 0xaf, 0x6f, 0xef,
                    209:        0x1f, 0x9f, 0x5f, 0xdf, 0x3f, 0xbf, 0x7f, 0xff,
                    210: };
                    211:
                    212: #endif
                    213:
                    214: static struct font *wsfont_find0(int);
                    215:
                    216: #if !defined(SMALL_KERNEL) || defined(__alpha__)
                    217:
                    218: /*
                    219:  * Reverse the bit order of a font
                    220:  */
                    221: static void    wsfont_revbit(struct wsdisplay_font *);
                    222: static void
                    223: wsfont_revbit(font)
                    224:        struct wsdisplay_font *font;
                    225: {
                    226:        u_char *p, *m;
                    227:
                    228:        p = (u_char *)font->data;
                    229:        m = p + font->stride * font->numchars * font->fontheight;
                    230:
                    231:        for (; p < m; p++)
                    232:                *p = reverse[*p];
                    233: }
                    234:
                    235: #endif
                    236:
                    237: #if !defined(SMALL_KERNEL)
                    238:
                    239: /*
                    240:  * Reverse the byte order of a font
                    241:  */
                    242: static void    wsfont_revbyte(struct wsdisplay_font *);
                    243: static void
                    244: wsfont_revbyte(font)
                    245:        struct wsdisplay_font *font;
                    246: {
                    247:        int x, l, r, nr;
                    248:        u_char *rp;
                    249:
                    250:        if (font->stride == 1)
                    251:                return;
                    252:
                    253:        rp = (u_char *)font->data;
                    254:        nr = font->numchars * font->fontheight;
                    255:
                    256:        while (nr--) {
                    257:                l = 0;
                    258:                r = font->stride - 1;
                    259:
                    260:                while (l < r) {
                    261:                        x = rp[l];
                    262:                        rp[l] = rp[r];
                    263:                        rp[r] = x;
                    264:                        l++, r--;
                    265:                }
                    266:
                    267:                rp += font->stride;
                    268:        }
                    269: }
                    270:
                    271: #endif
                    272:
                    273: /*
                    274:  * Enumerate the list of fonts
                    275:  */
                    276: void
                    277: wsfont_enum(cb)
                    278:        void (*cb)(char *, int, int, int);
                    279: {
                    280:        struct wsdisplay_font *f;
                    281:        struct font *ent;
                    282:        int s;
                    283:
                    284:        s = splhigh();
                    285:
                    286:        for (ent = list; ent; ent = ent->next) {
                    287:                f = ent->font;
                    288:                cb(f->name, f->fontwidth, f->fontheight, f->stride);
                    289:        }
                    290:
                    291:        splx(s);
                    292: }
                    293:
                    294: #if NRASOPS_ROTATION > 0
                    295:
                    296: struct wsdisplay_font *wsfont_rotate_internal(struct wsdisplay_font *);
                    297:
                    298: struct wsdisplay_font *
                    299: wsfont_rotate_internal(struct wsdisplay_font *font)
                    300: {
                    301:        int b, n, r, newstride;
                    302:        struct wsdisplay_font *newfont;
                    303:        char *newbits;
                    304:
                    305:        /* Duplicate the existing font... */
                    306:        newfont = malloc(sizeof *font, M_DEVBUF, M_WAITOK);
                    307:        if (newfont == NULL)
                    308:                return (NULL);
                    309:
                    310:        bcopy(font, newfont, sizeof *font);
                    311:        newfont->cookie = NULL;
                    312:
                    313:        /* Allocate a buffer big enough for the rotated font. */
                    314:        newstride = (font->fontheight + 7) / 8;
                    315:        newbits = malloc(newstride * font->fontwidth * font->numchars,
                    316:            M_DEVBUF, M_WAITOK);
                    317:        if (newbits == NULL) {
                    318:                free(newfont, M_DEVBUF);
                    319:                return (NULL);
                    320:        }
                    321:
                    322:        bzero(newbits, newstride * font->fontwidth * font->numchars);
                    323:
                    324:        /* Rotate the font a bit at a time. */
                    325:        for (n = 0; n < font->numchars; n++) {
                    326:                char *ch = font->data + (n * font->stride * font->fontheight);
                    327:
                    328:                for (r = 0; r < font->fontheight; r++) {
                    329:                        for (b = 0; b < font->fontwidth; b++) {
                    330:                                unsigned char *rb;
                    331:
                    332:                                rb = ch + (font->stride * r) + (b / 8);
                    333:                                if (*rb & (0x80 >> (b % 8))) {
                    334:                                        unsigned char *rrb;
                    335:
                    336:                                        rrb = newbits + newstride - 1 - (r / 8)
                    337:                                            + (n * newstride * font->fontwidth)
                    338:                                            + (newstride * b);
                    339:                                        *rrb |= (1 << (r % 8));
                    340:                                }
                    341:                        }
                    342:                }
                    343:        }
                    344:
                    345:        newfont->data = newbits;
                    346:
                    347:        /* Update font sizes. */
                    348:        newfont->stride = newstride;
                    349:        newfont->fontwidth = font->fontheight;
                    350:        newfont->fontheight = font->fontwidth;
                    351:
                    352:        if (wsfont_add(newfont, 0) != 0) {
                    353:                /*
                    354:                 * If we seem to have rotated this font already, drop the
                    355:                 * new one...
                    356:                 */
                    357:                free(newbits, M_DEVBUF);
                    358:                free(newfont, M_DEVBUF);
                    359:                newfont = NULL;
                    360:        }
                    361:
                    362:        return (newfont);
                    363: }
                    364:
                    365: int
                    366: wsfont_rotate(int cookie)
                    367: {
                    368:        int s, ncookie;
                    369:        struct wsdisplay_font *font;
                    370:        struct font *origfont;
                    371:
                    372:        s = splhigh();
                    373:        origfont = wsfont_find0(cookie);
                    374:        splx(s);
                    375:
                    376:        font = wsfont_rotate_internal(origfont->font);
                    377:        if (font == NULL)
                    378:                return (-1);
                    379:
                    380:        ncookie = wsfont_find(font->name, font->fontwidth, font->fontheight,
                    381:            font->stride);
                    382:
                    383:        return (ncookie);
                    384: }
                    385:
                    386: #endif /* NRASOPS_ROTATION */
                    387:
                    388: /*
                    389:  * Initialize list with WSFONT_BUILTIN fonts
                    390:  */
                    391: void
                    392: wsfont_init(void)
                    393: {
                    394:        static int again;
                    395:        int i;
                    396:
                    397:        if (again != 0)
                    398:                return;
                    399:        again = 1;
                    400:
                    401:        for (i = 0; builtin_fonts[i].font != NULL; i++) {
                    402:                builtin_fonts[i].next = list;
                    403:                list = &builtin_fonts[i];
                    404:        }
                    405: }
                    406:
                    407: /*
                    408:  * Find a font by cookie. Called at splhigh.
                    409:  */
                    410: static struct font *
                    411: wsfont_find0(cookie)
                    412:        int cookie;
                    413: {
                    414:        struct font *ent;
                    415:
                    416:        for (ent = list; ent != NULL; ent = ent->next)
                    417:                if (ent->cookie == cookie)
                    418:                        return (ent);
                    419:
                    420:        return (NULL);
                    421: }
                    422:
                    423: /*
                    424:  * Find a font.
                    425:  */
                    426: int
                    427: wsfont_find(name, width, height, stride)
                    428:        char *name;
                    429:        int width, height, stride;
                    430: {
                    431:        struct font *ent;
                    432:        int s;
                    433:
                    434:        s = splhigh();
                    435:
                    436:        for (ent = list; ent != NULL; ent = ent->next) {
                    437:                if (height != 0 && ent->font->fontheight != height)
                    438:                        continue;
                    439:
                    440:                if (width != 0 && ent->font->fontwidth != width)
                    441:                        continue;
                    442:
                    443:                if (stride != 0 && ent->font->stride != stride)
                    444:                        continue;
                    445:
                    446:                if (name != NULL && strcmp(ent->font->name, name) != 0)
                    447:                        continue;
                    448:
                    449:                splx(s);
                    450:                return (ent->cookie);
                    451:        }
                    452:
                    453:        splx(s);
                    454:        return (-1);
                    455: }
                    456:
                    457: /*
                    458:  * Add a font to the list.
                    459:  */
                    460: int
                    461: wsfont_add(font, copy)
                    462:        struct wsdisplay_font *font;
                    463:        int copy;
                    464: {
                    465:        static int cookiegen = 666;
                    466:        struct font *ent;
                    467:        size_t size;
                    468:        int s;
                    469:
                    470:        s = splhigh();
                    471:
                    472:        /* Don't allow exact duplicates */
                    473:        if (wsfont_find(font->name, font->fontwidth, font->fontheight,
                    474:            font->stride) >= 0) {
                    475:                splx(s);
                    476:                return (-1);
                    477:        }
                    478:
                    479:        MALLOC(ent, struct font *, sizeof *ent, M_DEVBUF, M_WAITOK);
                    480:
                    481:        ent->lockcount = 0;
                    482:        ent->flg = 0;
                    483:        ent->cookie = cookiegen++;
                    484:        ent->next = list;
                    485:        ent->prev = NULL;
                    486:
                    487:        /* Is this font statically allocated? */
                    488:        if (!copy) {
                    489:                ent->font = font;
                    490:                ent->flg = WSFONT_STATIC;
                    491:        } else {
                    492:                MALLOC(ent->font, struct wsdisplay_font *, sizeof *ent->font,
                    493:                    M_DEVBUF, M_WAITOK);
                    494:                memcpy(ent->font, font, sizeof(*ent->font));
                    495:
                    496:                size = font->fontheight * font->numchars * font->stride;
                    497:                MALLOC(ent->font->data, void *, size, M_DEVBUF, M_WAITOK);
                    498:                memcpy(ent->font->data, font->data, size);
                    499:                ent->flg = 0;
                    500:        }
                    501:
                    502:        /* Now link into the list and return */
                    503:        list = ent;
                    504:        splx(s);
                    505:        return (0);
                    506: }
                    507:
                    508: /*
                    509:  * Remove a font.
                    510:  */
                    511: #ifdef notyet
                    512: int
                    513: wsfont_remove(cookie)
                    514:        int cookie;
                    515: {
                    516:        struct font *ent;
                    517:        int s;
                    518:
                    519:        s = splhigh();
                    520:
                    521:        if ((ent = wsfont_find0(cookie)) == NULL) {
                    522:                splx(s);
                    523:                return (-1);
                    524:        }
                    525:
                    526:        if ((ent->flg & WSFONT_BUILTIN) != 0 || ent->lockcount != 0) {
                    527:                splx(s);
                    528:                return (-1);
                    529:        }
                    530:
                    531:        /* Don't free statically allocated font data */
                    532:        if ((ent->flg & WSFONT_STATIC) != 0) {
                    533:                FREE(ent->font->data, M_DEVBUF);
                    534:                FREE(ent->font, M_DEVBUF);
                    535:        }
                    536:
                    537:        /* Remove from list, free entry */
                    538:        if (ent->prev)
                    539:                ent->prev->next = ent->next;
                    540:        else
                    541:                list = ent->next;
                    542:
                    543:        if (ent->next)
                    544:                ent->next->prev = ent->prev;
                    545:
                    546:        FREE(ent, M_DEVBUF);
                    547:        splx(s);
                    548:        return (0);
                    549: }
                    550: #endif
                    551:
                    552: /*
                    553:  * Lock a given font and return new lockcount. This fails if the cookie
                    554:  * is invalid, or if the font is already locked and the bit/byte order
                    555:  * requested by the caller differs.
                    556:  */
                    557: int
                    558: wsfont_lock(cookie, ptr, bitorder, byteorder)
                    559:        int cookie;
                    560:        struct wsdisplay_font **ptr;
                    561:        int bitorder, byteorder;
                    562: {
                    563:        struct font *ent;
                    564:        int s, lc;
                    565:
                    566:        s = splhigh();
                    567:
                    568:        if ((ent = wsfont_find0(cookie)) != NULL) {
                    569:                if (bitorder && bitorder != ent->font->bitorder) {
                    570: #if !defined(SMALL_KERNEL) || defined(__alpha__)
                    571:                        if (ent->lockcount) {
                    572:                                splx(s);
                    573:                                return (-1);
                    574:                        }
                    575:                        wsfont_revbit(ent->font);
                    576:                        ent->font->bitorder = bitorder;
                    577: #else
                    578:                        splx(s);
                    579:                        return (-1);
                    580: #endif
                    581:                }
                    582:
                    583:                if (byteorder && byteorder != ent->font->byteorder) {
                    584: #if !defined(SMALL_KERNEL)
                    585:                        if (ent->lockcount) {
                    586:                                splx(s);
                    587:                                return (-1);
                    588:                        }
                    589:                        wsfont_revbyte(ent->font);
                    590:                        ent->font->byteorder = byteorder;
                    591: #else
                    592:                        splx(s);
                    593:                        return (-1);
                    594: #endif
                    595:                }
                    596:
                    597:                lc = ++ent->lockcount;
                    598:                *ptr = ent->font;
                    599:        } else
                    600:                lc = -1;
                    601:
                    602:        splx(s);
                    603:        return (lc);
                    604: }
                    605:
                    606: /*
                    607:  * Get font flags and lockcount.
                    608:  */
                    609: int
                    610: wsfont_getflg(cookie, flg, lc)
                    611:        int cookie, *flg, *lc;
                    612: {
                    613:        struct font *ent;
                    614:        int s;
                    615:
                    616:        s = splhigh();
                    617:
                    618:        if ((ent = wsfont_find0(cookie)) != NULL) {
                    619:                *flg = ent->flg;
                    620:                *lc = ent->lockcount;
                    621:        }
                    622:
                    623:        splx(s);
                    624:        return (ent != NULL ? 0 : -1);
                    625: }
                    626:
                    627: /*
                    628:  * Unlock a given font and return new lockcount.
                    629:  */
                    630: int
                    631: wsfont_unlock(cookie)
                    632:        int cookie;
                    633: {
                    634:        struct font *ent;
                    635:        int s, lc;
                    636:
                    637:        s = splhigh();
                    638:
                    639:        if ((ent = wsfont_find0(cookie)) != NULL) {
                    640:                if (ent->lockcount == 0)
                    641:                        panic("wsfont_unlock: font not locked");
                    642:                lc = --ent->lockcount;
                    643:        } else
                    644:                lc = -1;
                    645:
                    646:        splx(s);
                    647:        return (lc);
                    648: }
                    649:
                    650: #if !defined(SMALL_KERNEL)
                    651:
                    652: /*
                    653:  * Unicode to font encoding mappings
                    654:  */
                    655:
                    656: /*
                    657:  * To save memory, font encoding tables use a two level lookup.
                    658:  * First the high byte of the Unicode is used to lookup the level 2
                    659:  * table, then the low byte indexes that table.  Level 2 tables that are
                    660:  * not needed are omitted (NULL), and both level 1 and level 2 tables
                    661:  * have base and size attributes to keep their size down.
                    662:  */
                    663:
                    664: struct wsfont_level1_glyphmap {
                    665:        struct wsfont_level2_glyphmap **level2;
                    666:        int base;       /* High byte for first level2 entry     */
                    667:        int size;       /* Number of level2 entries             */
                    668: };
                    669:
                    670: struct wsfont_level2_glyphmap {
                    671:        int base;       /* Low byte for first character         */
                    672:        int size;       /* Number of characters                 */
                    673:        void *chars;    /* Pointer to character number entries  */
                    674:        int width;      /* Size of each entry in bytes (1,2,4)  */
                    675: };
                    676:
                    677: #define null16                 \
                    678:        NULL, NULL, NULL, NULL, \
                    679:        NULL, NULL, NULL, NULL, \
                    680:        NULL, NULL, NULL, NULL, \
                    681:        NULL, NULL, NULL, NULL
                    682:
                    683: /*
                    684:  * IBM 437 maps
                    685:  */
                    686:
                    687: static u_int8_t
                    688: ibm437_chars_0[] = {
                    689:         0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15,
                    690:        16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
                    691:        32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47,
                    692:        48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63,
                    693:        64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79,
                    694:        80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95,
                    695:        96, 97, 98, 99, 100,101,102,103,104,105,106,107,108,109,110,111,
                    696:        112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,
                    697:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    698:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    699:        255,173,155,156, 0, 157, 0,  0,  0,  0, 166,174,170, 0,  0,  0,
                    700:         0, 241,253, 0,  0,  0,  0, 249, 0,  0, 167,175,172,171, 0, 168,
                    701:         0,  0,  0,  0, 142,143,146,128, 0, 144, 0,  0,  0,  0,  0,  0,
                    702:         0, 165, 0,  0,  0,  0, 153, 0,  0,  0,  0,  0, 154, 0,  0,  0,
                    703:        133,160,131, 0, 132,134,145,135,138,130,136,137,141,161,140,139,
                    704:         0, 164,149,162,147, 0, 148,246, 0, 151,163,150,129, 0,  0, 152
                    705: },
                    706: ibm437_chars_1[] = {
                    707:        159
                    708: },
                    709: ibm437_chars_3[] = {
                    710:        226, 0,  0,  0,  0, 233, 0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    711:        228, 0,  0, 232, 0,  0, 234, 0,  0,  0,  0,  0,  0,  0, 224,225,
                    712:         0, 235,238, 0,  0,  0,  0,  0,  0, 230, 0,  0,  0, 227, 0,  0,
                    713:        229,231
                    714: },
                    715: ibm437_chars_32[] = {
                    716:        252, 0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    717:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    718:         0,  0,  0,  0,  0,  0,  0,  0, 158
                    719: },
                    720: ibm437_chars_34[] = {
                    721:        237, 0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    722:         0,  0,  0, 248,250,251, 0,  0,  0, 236, 0,  0,  0,  0,  0,  0,
                    723:         0,  0,  0,  0, 239, 0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    724:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    725:         0,  0,  0, 247, 0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    726:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,240,  0,  0,243,
                    727:        242
                    728: },
                    729: ibm437_chars_35[] = {
                    730:        169, 0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    731:        244,245
                    732: },
                    733: ibm437_chars_37[] = {
                    734:        196,205,179,186, 0,  0,  0,  0,  0,  0,  0,  0, 218,213,214,201,
                    735:        191,184,183,187,192,212,211,200,217,190,189,188,195,198, 0,  0,
                    736:        199, 0,  0, 204,180,181, 0,  0, 182, 0,  0, 185,194, 0,  0, 209,
                    737:        210, 0,  0, 203,193, 0,  0, 207,208, 0,  0, 202,197, 0,  0, 216,
                    738:         0,  0, 215, 0,  0,  0,  0,  0,  0,  0,  0, 206, 0,  0,  0,  0,
                    739:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    740:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    741:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    742:        223, 0,  0,  0, 220, 0,  0,  0, 219, 0,  0,  0, 221, 0,  0,  0,
                    743:        222,176,177,178, 0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    744:        254
                    745: };
                    746:
                    747: static struct wsfont_level2_glyphmap
                    748: ibm437_level2_0 = { 0, 256, ibm437_chars_0, 1 },
                    749: ibm437_level2_1 = { 146, 1, ibm437_chars_1, 1 },
                    750: ibm437_level2_3 = { 147, 50, ibm437_chars_3, 1 },
                    751: ibm437_level2_32 = { 127, 41, ibm437_chars_32, 1 },
                    752: ibm437_level2_34 = { 5, 97, ibm437_chars_34, 1 },
                    753: ibm437_level2_35 = { 16, 18, ibm437_chars_35, 1 },
                    754: ibm437_level2_37 = { 0, 161, ibm437_chars_37, 1 };
                    755:
                    756: static struct wsfont_level2_glyphmap *ibm437_level1[] = {
                    757:        &ibm437_level2_0, &ibm437_level2_1, NULL, &ibm437_level2_3,
                    758:        NULL, NULL, NULL, NULL,
                    759:        NULL, NULL, NULL, NULL,
                    760:        NULL, NULL, NULL, NULL,
                    761:        NULL, NULL, NULL, NULL,
                    762:        NULL, NULL, NULL, NULL,
                    763:        NULL, NULL, NULL, NULL,
                    764:        NULL, NULL, NULL, NULL,
                    765:        &ibm437_level2_32, NULL, &ibm437_level2_34, &ibm437_level2_35,
                    766:        NULL, &ibm437_level2_37
                    767: };
                    768:
                    769:
                    770: /*
                    771:  * ISO-8859-7 maps
                    772:  */
                    773:
                    774: static u_int8_t
                    775: iso7_chars_0[] = {
                    776:         0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15,
                    777:        16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
                    778:        32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47,
                    779:        48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 62, 63,
                    780:        64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79,
                    781:        80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 91, 92, 93, 94, 95,
                    782:        96, 97, 98, 99, 100,101,102,103,104,105,106,107,108,109,110,111,
                    783:        112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,
                    784:        128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,
                    785:        144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,
                    786:        160, 0,  0, 163, 0,  0, 166,167,168,169, 0, 171,172,173, 0,  0,
                    787:        176,177,178,179,180, 0,  0, 183, 0,  0,  0, 187, 0, 189
                    788: },
                    789: iso7_chars_3[] = {
                    790:        182, 0, 184,185,186, 0, 188, 0, 190,191,192,193,194,195,196,197,
                    791:        198,199,200,201,202,203,204,205,206,207,208,209, 0, 211,212,213,
                    792:        214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,
                    793:        230,231,232,233,234,235,236,237,238,239,240,241,242,243,244,245,
                    794:        246,247,248,249,250,251,252,253,254, 0,  0,  0,  0,  0,  0,  0,
                    795:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,
                    796:         0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0,  0, 181
                    797: },
                    798: iso7_chars_32[] = {
                    799:        175, 0,  0,  0,  0, 162, 0, 161
                    800: };
                    801:
                    802: static struct wsfont_level2_glyphmap
                    803: iso7_level2_0 = { 0, 190, iso7_chars_0, 1 },
                    804: iso7_level2_3 = { 134, 111, iso7_chars_3, 1 },
                    805: iso7_level2_32 = { 20, 8, iso7_chars_32, 1 };
                    806:
                    807: static struct wsfont_level2_glyphmap *iso7_level1[] = {
                    808:        &iso7_level2_0, NULL, NULL, &iso7_level2_3,
                    809:        NULL, NULL, NULL, NULL,
                    810:        NULL, NULL, NULL, NULL,
                    811:        NULL, NULL, NULL, NULL,
                    812:        NULL, NULL, NULL, NULL,
                    813:        NULL, NULL, NULL, NULL,
                    814:        NULL, NULL, NULL, NULL,
                    815:        NULL, NULL, NULL, NULL,
                    816:        &iso7_level2_32
                    817: };
                    818:
                    819:
                    820: static struct wsfont_level1_glyphmap encodings[] = {
                    821:        { NULL, 0, 0 },                 /* WSDISPLAY_FONTENC_ISO */
                    822:        { ibm437_level1, 0, 38 },       /* WSDISPLAY_FONTENC_IBM */
                    823:        { NULL, 0, 0 },                 /* WSDISPLAY_FONTENC_PCVT */
                    824:        { iso7_level1, 0, 33 },         /* WSDISPLAY_FONTENC_ISO7 */
                    825: };
                    826:
                    827: #define MAX_ENCODING (sizeof(encodings) / sizeof(encodings[0]))
                    828:
                    829: #endif /* !SMALL_KERNEL */
                    830:
                    831: /*
                    832:  * Remap Unicode character to glyph
                    833:  */
                    834: int
                    835: wsfont_map_unichar(font, c)
                    836:        struct wsdisplay_font *font;
                    837:        int c;
                    838: {
                    839:        if (font->encoding == WSDISPLAY_FONTENC_ISO)
                    840:                return c;
                    841:        else
                    842: #if !defined(SMALL_KERNEL)
                    843:        if (font->encoding < 0 || font->encoding > MAX_ENCODING)
                    844:                return (-1);
                    845:        else {
                    846:                int hi = (c >> 8), lo = c & 255;
                    847:                struct wsfont_level1_glyphmap *map1 =
                    848:                        &encodings[font->encoding];
                    849:
                    850:                if (hi >= map1->base && hi < map1->base + map1->size) {
                    851:                        struct wsfont_level2_glyphmap *map2 =
                    852:                          map1->level2[hi - map1->base];
                    853:
                    854:                        if (map2 != NULL &&
                    855:                            lo >= map2->base && lo < map2->base + map2->size) {
                    856:
                    857:                                lo -= map2->base;
                    858:
                    859:                                switch(map2->width) {
                    860:                                case 1:
                    861:                                        c = (((u_int8_t *)map2->chars)[lo]);
                    862:                                        break;
                    863:                                case 2:
                    864:                                        c = (((u_int16_t *)map2->chars)[lo]);
                    865:                                        break;
                    866:                                case 4:
                    867:                                        c = (((u_int32_t *)map2->chars)[lo]);
                    868:                                        break;
                    869:                                }
                    870:
                    871:                                if (c == 0 && lo != 0)
                    872:                                        return (-1);
                    873:                                else
                    874:                                        return (c);
                    875:
                    876:                        } else {
                    877:                                return (-1);
                    878:                        }
                    879:
                    880:                } else {
                    881:                        return (-1);
                    882:                }
                    883:
                    884:        }
                    885: #else
                    886:        return (-1);
                    887: #endif /* SMALL_KERNEL */
                    888: }

CVSweb