Annotation of driverkit/libDriver/Kernel/IOSVGADisplay.m, revision 1.1

1.1     ! root        1: /*
        !             2:  * Copyright (c) 1999 Apple Computer, Inc. All rights reserved.
        !             3:  *
        !             4:  * @APPLE_LICENSE_HEADER_START@
        !             5:  * 
        !             6:  * Portions Copyright (c) 1999 Apple Computer, Inc.  All Rights
        !             7:  * Reserved.  This file contains Original Code and/or Modifications of
        !             8:  * Original Code as defined in and that are subject to the Apple Public
        !             9:  * Source License Version 1.1 (the "License").  You may not use this file
        !            10:  * except in compliance with the License.  Please obtain a copy of the
        !            11:  * License at http://www.apple.com/publicsource and read it before using
        !            12:  * this file.
        !            13:  * 
        !            14:  * The Original Code and all software distributed under the License are
        !            15:  * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
        !            16:  * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
        !            17:  * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
        !            18:  * FITNESS FOR A PARTICULAR PURPOSE OR NON- INFRINGEMENT.  Please see the
        !            19:  * License for the specific language governing rights and limitations
        !            20:  * under the License.
        !            21:  * 
        !            22:  * @APPLE_LICENSE_HEADER_END@
        !            23:  */
        !            24: /*     Copyright (c) 1993 NeXT Computer, Inc.  All rights reserved. 
        !            25:  *
        !            26:  * IOSVGADisplay.m - Implements common methods for SVGA display driver class.
        !            27:  *
        !            28:  *
        !            29:  * HISTORY
        !            30:  * 07 July 93  Scott Forstall
        !            31:  *      Created from earlier work by Joe Pasqua and Gary Crum.
        !            32:  */
        !            33: 
        !            34: #define KERNEL_PRIVATE 1
        !            35: #define DRIVER_PRIVATE 1
        !            36: 
        !            37: /* Notes:
        !            38:  *   This class implements the evScreen protocol for all IOSVGADisplays. Well,
        !            39:  *   almost. The setBrightness method doesn't do anything. Subclasses must
        !            40:  *   override this and implement it as appropriate for the device.
        !            41:  *
        !            42:  *   To find things that need to be fixed, search for FIX, to find questions
        !            43:  *   to be resolved, search for QUESTION, to find stuff that still needs to be
        !            44:  *   done, search for TO DO.
        !            45:  */
        !            46: 
        !            47: #import <string.h>
        !            48: #import <stdlib.h>
        !            49: #import <bsd/dev/i386/VGAConsole.h>
        !            50: #import <stdio.h>
        !            51: #import        <driverkit/EventDriver.h>
        !            52: #import        <bsd/dev/evio.h>
        !            53: #import        <bsd/dev/i386/kmDevice.h>
        !            54: #import <driverkit/KernBus.h>
        !            55: #import <driverkit/KernBusMemory.h>
        !            56: #import <driverkit/IODisplayPrivate.h>
        !            57: #import <driverkit/IOSVGADisplay.h>
        !            58: #import <driverkit/IOVGAShared.h>
        !            59: #import <driverkit/i386/directDevice.h>
        !            60: #import <driverkit/i386/driverTypes.h>
        !            61: 
        !            62: 
        !            63: //
        !            64: // BEGIN:      Defines used in this file
        !            65: //
        !            66: 
        !            67: #define CURSOR_WIDTH_IN_PIXELS 16
        !            68: #define PPXMASK ((unsigned int)0x0000000f)
        !            69: 
        !            70: #if (SWAPBITS == DEVICE_CONSISTENT)
        !            71: #define LSHIFT >>
        !            72: #define RSHIFT <<
        !            73: #define LSHIFTEQ >>=
        !            74: #define RSHIFTEQ <<=
        !            75: #else (SWAPBITS == DEVICE_CONSISTENT)
        !            76: #define LSHIFT <<
        !            77: #define RSHIFT >>
        !            78: #define LSHIFTEQ <<=
        !            79: #define RSHIFTEQ >>=
        !            80: #endif (SWAPBITS == DEVICE_CONSISTENT)
        !            81: 
        !            82: #define CLEAR_SEMAPHORE(shmem) \
        !            83:        ev_unlock(&shmem->cursorSema)
        !            84: #define SET_SEMAPHORE(shmem) \
        !            85:        if (!ev_try_lock(&shmem->cursorSema)) return self
        !            86: #define RECTS_INTERSECT(one, two) \
        !            87:        (((one.minx < two.maxx) && (two.minx < one.maxx)) && \
        !            88:        ((one.miny < two.maxy) && (two.miny < one.maxy)))
        !            89: 
        !            90: //
        !            91: // END:                Defines used in this file
        !            92: //
        !            93: 
        !            94: 
        !            95: @implementation IOSVGADisplay
        !            96: 
        !            97: //
        !            98: // BEGIN:      Implementation of private routines for SVGA
        !            99: //
        !           100: 
        !           101: 
        !           102: - (VGAShmem_t *)_shmem
        !           103: // Description:        Return IOSVGADisplay's shared memory which is
        !           104: //             stored in a private instance variable.
        !           105: {
        !           106:     return (VGAShmem_t *)_priv;
        !           107: }
        !           108: 
        !           109: 
        !           110: - (IOReturn)_registerWithED
        !           111: // Description:        Register this display device with the event driver.
        !           112: //             Set up and initialize the shared memory.
        !           113: {
        !           114:     int shmem_size;
        !           115:     Bounds bounds;
        !           116:     int token;
        !           117:     VGAShmem_t *shmem;
        !           118:     
        !           119:     token = [[EventDriver instance] registerScreen:self
        !           120:        bounds:&bounds
        !           121:        shmem:&(self->_priv)
        !           122:        size:&shmem_size];
        !           123:     shmem = [self _shmem];
        !           124:     
        !           125:     if ( token == -1 ) {
        !           126:        return IO_R_INVALID_ARG;
        !           127:     }
        !           128:     
        !           129:     // We allow the shmem_size to be less than sizeof(VGAShmem_t)
        !           130:     // so that we need not consume the extra space that some of the
        !           131:     // larger cursor variants require if we are really a lower bitdepth.
        !           132:     if ( shmem_size > sizeof(VGAShmem_t) ) {
        !           133:        IOLog("%s: shmem_size > sizeof (VGAShmem_t)(%d<>%d)\n",
        !           134:            [self name], shmem_size, sizeof (VGAShmem_t));
        !           135:        [[EventDriver instance] unregisterScreen:token];
        !           136:        return IO_R_INVALID_ARG;
        !           137:     }
        !           138:     
        !           139:     // Init shared memory area
        !           140:     bzero( (char *)shmem, shmem_size );
        !           141:     shmem->cursorShow = 1;
        !           142:     shmem->screenBounds = bounds;
        !           143:     [self setToken:token];
        !           144:     
        !           145:     return IO_R_SUCCESS;
        !           146: }
        !           147: 
        !           148: 
        !           149: - (void)_readBpp4planar: (unsigned short *)fb toBpp2packed32: (unsigned int *)dst
        !           150: // Description:        reads in a 4-planar representation, converts it into a
        !           151: //             packed-32 representation, and writes the result into
        !           152: //             dst.
        !           153: {
        !           154:     unsigned int v, i;
        !           155:     
        !           156:     [self setReadPlane: 1];
        !           157:     i = 0xffff ^ *fb;
        !           158:     v =   (i & 0x8000) <<  2 | (i & 0x4000) <<  5 | (i & 0x2000) <<  8
        !           159:        | (i & 0x1000) << 11 | (i & 0x0800) << 14 | (i & 0x0400) << 17
        !           160:        | (i & 0x0200) << 20 | (i & 0x0100) << 23 | (i & 0x0080) >>  6
        !           161:        | (i & 0x0040) >>  3 | (i & 0x0020)       | (i & 0x0010) <<  3
        !           162:        | (i & 0x0008) <<  6 | (i & 0x0004) <<  9 | (i & 0x0002) << 12
        !           163:        | (i & 0x0001) << 15;
        !           164: 
        !           165:     [self setReadPlane: 0];
        !           166:     i = 0xffff ^ *fb;
        !           167:     v |=  (i & 0x8000) <<  1 | (i & 0x4000) <<  4 | (i & 0x2000) <<  7
        !           168:        | (i & 0x1000) << 10 | (i & 0x0800) << 13 | (i & 0x0400) << 16
        !           169:        | (i & 0x0200) << 19 | (i & 0x0100) << 22 | (i & 0x0080) >>  7
        !           170:        | (i & 0x0040) >>  4 | (i & 0x0020) >>  1 | (i & 0x0010) <<  2
        !           171:        | (i & 0x0008) <<  5 | (i & 0x0004) <<  8 | (i & 0x0002) << 11
        !           172:        | (i & 0x0001) << 14;
        !           173: 
        !           174:     *dst = v;
        !           175: }
        !           176: 
        !           177: - (void)_writeBpp2packed32: (unsigned int *)dst toBpp4planar: (unsigned short *)fb
        !           178: // Description:        reads in a packed-32 representation, converts it into a
        !           179: //             4-planar representation, and writes the result into
        !           180: //             fb.
        !           181: {
        !           182:     unsigned int i, dstvalue;
        !           183:     unsigned short fbvalue;
        !           184:     unsigned char fblo, fbhi;
        !           185: 
        !           186:     [self setWritePlane: 1];
        !           187:     dstvalue = *dst;
        !           188:     i = dstvalue & 0xAAAA;
        !           189:     fblo = 0xff ^ (char) (((i & 0x8000) >> 15) | ((i & 0x2000) >> 12)
        !           190:                        | ((i & 0x0800) >>  9) | ((i & 0x0200) >> 6)
        !           191:                        | ((i & 0x0080) >>  3) |  (i & 0x0020)
        !           192:                        | ((i & 0x0008) <<  3) | ((i & 0x0002) << 6));
        !           193:     i = (dstvalue >> 16) & 0xAAAA;
        !           194:     fbhi = 0xff ^ (char) (((i & 0x8000) >> 15) | ((i & 0x2000) >> 12)
        !           195:                        | ((i & 0x0800) >>  9) | ((i & 0x0200) >> 6)
        !           196:                        | ((i & 0x0080) >>  3) |  (i & 0x0020)
        !           197:                        | ((i & 0x0008) <<  3) | ((i & 0x0002) << 6));
        !           198:     fbvalue = (((unsigned short)fbhi) << 8) | fblo;
        !           199:     *fb = fbvalue;
        !           200: 
        !           201:     [self setWritePlane: 0];
        !           202:     dstvalue = *dst;
        !           203:     i = dstvalue & 0x5555;
        !           204:     fblo = 0xff ^ (char) (((i & 0x4000) >> 14) | ((i & 0x1000) >> 11)
        !           205:                        | ((i & 0x0400) >>  8) | ((i & 0x0100) >> 5)
        !           206:                        | ((i & 0x0040) >>  2) | ((i & 0x0010) << 1)
        !           207:                        | ((i & 0x0004) <<  4) | ((i & 0x0001) << 7));
        !           208:     i = (dstvalue >> 16) & 0x5555;
        !           209:     fbhi = 0xff ^ (char) (((i & 0x4000) >> 14) | ((i & 0x1000) >> 11)
        !           210:                        | ((i & 0x0400) >>  8) | ((i & 0x0100) >> 5)
        !           211:                        | ((i & 0x0040) >>  2) | ((i & 0x0010) << 1)
        !           212:                        | ((i & 0x0004) <<  4) | ((i & 0x0001) << 7));
        !           213:     fbvalue = (((unsigned short)fbhi) << 8) | fblo;
        !           214:     *fb = fbvalue;
        !           215: }
        !           216: 
        !           217: 
        !           218: - (void)_VGADisplayCursor: (IODisplayInfo *)dpy shmem: (VGAShmem_t *)shmem
        !           219: // Description: Displays the cursor on the framebuffer by first saving
        !           220: //             what's underneath the cursor, then drawing the cursor there.
        !           221: //             NOTE:The topleft of the cursorRect passed in is not
        !           222: //             necessarily the cursor location.The cursorRect is adjusted to
        !           223: //             compensate for the cursor hotspot.If the frame buffer is
        !           224: //             cacheable, flush at the end of the drawing operation. A
        !           225: //             saveRect is stored which defines the actual area of the screen
        !           226: //             that is saved.This is used by RemoveCursor in restoring the
        !           227: //             screen data later.
        !           228: {
        !           229:     Bounds screenBounds = shmem->screenBounds;
        !           230:     Bounds saveRect;           /* cursor save rectangle (local) */
        !           231:     unsigned int *cursPtr;     /* cursor data pointer */
        !           232:     unsigned int *vramPtr;     /* screen data pointer */
        !           233:     unsigned int *savePtr;     /* saved screen data pointer */
        !           234:     unsigned int *maskPtr;     /* cursor mask pointer */
        !           235:     int i, doLeft, doRight, skew, rSkew;
        !           236:     static unsigned int vramBuf[2];
        !           237:     unsigned short *this_segment, *fb;
        !           238:     unsigned int fb_x_offset_shorts;
        !           239:     unsigned int fb_shorts_per_line;
        !           240:     unsigned int fb_lines_per_segment;
        !           241:     unsigned int fb_segment;
        !           242:     unsigned int fb_next_segment_y;
        !           243:     int y;
        !           244:     int miny, maxy;            /* absolute min and max y--not relative address */
        !           245:                                /* e.g. 0 <= miny <= SCREEN_HEIGHT */
        !           246: 
        !           247:     [self savePlaneAndSegmentSettings];
        !           248: 
        !           249:     saveRect = shmem->cursorRect;
        !           250:     vramPtr = (unsigned int *)vramBuf;
        !           251: 
        !           252:     //
        !           253:     // Clip saveRect vertical within screen bounds
        !           254:     //
        !           255:     if (saveRect.miny < screenBounds.miny) {
        !           256:        saveRect.miny = screenBounds.miny;
        !           257:     }
        !           258:     if (saveRect.maxy > screenBounds.maxy) {
        !           259:        saveRect.maxy = screenBounds.maxy;
        !           260:     }
        !           261:     i = shmem->cursorRect.minx - screenBounds.minx;
        !           262:     saveRect.minx = i - (i & PPXMASK) + screenBounds.minx;
        !           263:     saveRect.maxx = saveRect.minx + CURSORWIDTH*2;
        !           264:     shmem->saveRect = saveRect;
        !           265: 
        !           266:     //
        !           267:     // skew is in bits
        !           268:     //
        !           269:     skew = (shmem->cursorRect.minx & PPXMASK)<<1;
        !           270:     rSkew = 32-skew;
        !           271: 
        !           272:     //
        !           273:     // Set up pointers for saving and drawing
        !           274:     //
        !           275:     cursPtr = shmem->cursor.bw.image[shmem->frame];
        !           276:     maskPtr = shmem->cursor.bw.mask[shmem->frame];
        !           277:     savePtr = shmem->cursor.bw.save;
        !           278:     i = saveRect.miny - shmem->cursorRect.miny;
        !           279:     cursPtr += i;
        !           280:     maskPtr += i;
        !           281: 
        !           282:     //
        !           283:     // Since we are drawing an int at a time, and it may
        !           284:     // cross an int boundary, we draw it in two pieces (left
        !           285:     // and right) which are offset by skew.
        !           286:     //
        !           287:     doLeft =  (saveRect.minx >= screenBounds.minx);
        !           288:     doRight = (saveRect.maxx <= screenBounds.maxx);
        !           289: 
        !           290:     //
        !           291:     // VGA related assignments
        !           292:     //
        !           293:     // QUESTION--isn't this a little fishy??  Should this be the address we mapped?
        !           294:     this_segment = (unsigned short *)(0xa0000);
        !           295:     fb_x_offset_shorts = (saveRect.minx - screenBounds.minx) >> 4;
        !           296:     fb_shorts_per_line = dpy->width >> 4;
        !           297:     fb_lines_per_segment = 0x10000 / (dpy->width >> 3);
        !           298:     
        !           299:     miny = saveRect.miny - screenBounds.miny;
        !           300:     maxy = saveRect.maxy - screenBounds.miny;
        !           301:     
        !           302:     fb =    this_segment +
        !           303:            ((miny % fb_lines_per_segment) * fb_shorts_per_line) +
        !           304:            fb_x_offset_shorts;
        !           305:     fb_segment = miny / fb_lines_per_segment;
        !           306:     fb_next_segment_y = (fb_lines_per_segment * (fb_segment + 1));
        !           307:     
        !           308:     [self setWriteSegment: fb_segment];
        !           309:     [self setReadSegment: fb_segment];
        !           310: 
        !           311:     for (   y = miny;
        !           312:            y < maxy;
        !           313:            y++) {
        !           314:        register unsigned int workreg;
        !           315: 
        !           316:        //
        !           317:        // Change VGA segment if necessary.
        !           318:        //
        !           319:        if (y == fb_next_segment_y) {
        !           320:            fb =    this_segment + 
        !           321:                    ((y % fb_lines_per_segment) * fb_shorts_per_line) +
        !           322:                    fb_x_offset_shorts;
        !           323:            fb_segment++;
        !           324:            fb_next_segment_y += fb_lines_per_segment;
        !           325:            
        !           326:            [self setWriteSegment: fb_segment];
        !           327:            [self setReadSegment: fb_segment];
        !           328:        }
        !           329: 
        !           330:        if (doLeft) {
        !           331:            [self _readBpp4planar:fb toBpp2packed32:vramPtr];
        !           332:            *savePtr++ = workreg = *vramPtr;
        !           333:            *vramPtr =  (workreg&(~((*maskPtr) RSHIFT skew))) |
        !           334:                        ((*cursPtr) RSHIFT skew);
        !           335:            [self _writeBpp2packed32:vramPtr toBpp4planar:fb];
        !           336:        }
        !           337:        if (doRight) {
        !           338:            if (!skew) {
        !           339:                savePtr++;
        !           340:            } else {
        !           341:                [self _readBpp4planar:(fb+1) toBpp2packed32:(vramPtr+1)];
        !           342:                *savePtr++ = workreg = *(vramPtr+1);
        !           343:                *(vramPtr+1)=   (workreg&(~((*maskPtr) LSHIFT rSkew))) |
        !           344:                                ((*cursPtr) LSHIFT rSkew);
        !           345:                [self _writeBpp2packed32:(vramPtr+1) toBpp4planar:(fb+1)];
        !           346:            }
        !           347:        }
        !           348: 
        !           349:        //
        !           350:        // Advance fb (pointer into VGA framebuffer) one line.
        !           351:        //
        !           352:        fb += fb_shorts_per_line;
        !           353: 
        !           354:        cursPtr++;
        !           355:        maskPtr++;
        !           356:     }
        !           357: 
        !           358:     [self restorePlaneAndSegmentSettings];
        !           359: }
        !           360: 
        !           361: 
        !           362: - (void)_VGARemoveCursor: (IODisplayInfo *)dpy shmem: (VGAShmem_t *)shmem
        !           363: // Description:        RemoveCursor erases the cursor by replacing the background
        !           364: //             image that was saved by the previous call to DisplayCursor.
        !           365: //             If the frame buffer is cacheable, flush at the end of the
        !           366: //             drawing operation.
        !           367: {
        !           368:     int doLeft, doRight;
        !           369:     unsigned int lmask = 0, rmask = 0;
        !           370:     unsigned int *vramPtr;
        !           371:     unsigned int *savePtr;
        !           372:     Bounds screenBounds = shmem->screenBounds;
        !           373:     Bounds saveRect = shmem->saveRect;
        !           374: #if __BIG_ENDIAN__
        !           375:     static const unsigned int mask_array[16] = {
        !           376:        0xFFFFFFFF,0x3FFFFFFF,0x0FFFFFFF,0x03FFFFFF,
        !           377:        0x00FFFFFF,0x003FFFFF,0x000FFFFF,0x0003FFFF,
        !           378:        0x0000FFFF,0x00003FFF,0x00000FFF,0x000003FF,
        !           379:        0x000000FF,0x0000003f,0x0000000F,0x00000003
        !           380:     };
        !           381: #else
        !           382:     static unsigned int mask_array[17] = {
        !           383:        0xFFFFFFFF,0xFFFFFFFC,0xFFFFFFF0,0xFFFFFFC0,
        !           384:        0xFFFFFF00,0xFFFFFC00,0xFFFFF000,0xFFFFC000,
        !           385:        0xFFFF0000,0xFFFC0000,0xFFF00000,0xFFC00000,
        !           386:         0xFF000000,0xFC000000,0xF0000000,0xC0000000,0x00000000};
        !           387: #endif
        !           388:     static unsigned int vramBuf[2];
        !           389:     unsigned short *this_segment, *fb;
        !           390:     unsigned int fb_x_offset_shorts;
        !           391:     unsigned int fb_shorts_per_line;
        !           392:     unsigned int fb_lines_per_segment;
        !           393:     unsigned int fb_segment;
        !           394:     unsigned int fb_next_segment_y;
        !           395:     int y;
        !           396:     int skew;
        !           397:     int miny, maxy;            /* absolute min and max y--not relative address */
        !           398:                                /* e.g. 0 <= miny <= SCREEN_HEIGHT */
        !           399: 
        !           400:     [self savePlaneAndSegmentSettings];
        !           401: 
        !           402:     vramPtr = (unsigned int *)vramBuf;
        !           403: 
        !           404:     //
        !           405:     // VGA related assignments
        !           406:     //
        !           407:     // QUESTION--isn't this a little fishy??  Should this be the address we mapped?
        !           408:     this_segment = (unsigned short *)(0xa0000);
        !           409:     fb_x_offset_shorts = (saveRect.minx - screenBounds.minx) >> 4;
        !           410:     fb_shorts_per_line = dpy->width >> 4;
        !           411:     
        !           412:     miny = saveRect.miny - screenBounds.miny;
        !           413:     maxy = saveRect.maxy - screenBounds.miny;
        !           414:     
        !           415:     //
        !           416:     // VGA bank size is 64K
        !           417:     //
        !           418:     fb_lines_per_segment = 0x10000 / (dpy->width >> 3);
        !           419:     fb =    this_segment +
        !           420:            ((miny % fb_lines_per_segment) * fb_shorts_per_line) +
        !           421:            fb_x_offset_shorts;
        !           422:     fb_segment = miny / fb_lines_per_segment;
        !           423:     fb_next_segment_y = (fb_lines_per_segment * (fb_segment + 1));
        !           424:     
        !           425:     [self setWriteSegment: fb_segment];
        !           426:     [self setReadSegment: fb_segment];
        !           427: 
        !           428:     //
        !           429:     // skew is in bits
        !           430:     //
        !           431:     skew = (shmem->cursorRect.minx & PPXMASK)<<1;
        !           432: 
        !           433:     savePtr = shmem->cursor.bw.save;
        !           434:     if (doLeft = (saveRect.minx >= screenBounds.minx)) {
        !           435:        lmask = mask_array[shmem->oldCursorRect.minx - saveRect.minx];
        !           436:     }
        !           437:     if (doRight = (saveRect.maxx <= screenBounds.maxx)) {
        !           438:        rmask = ~mask_array[16-(saveRect.maxx - shmem->oldCursorRect.maxx)];
        !           439:     }
        !           440:        
        !           441:     for (   y = miny;
        !           442:            y < maxy;
        !           443:            y++) {
        !           444: 
        !           445:        //
        !           446:        // Change VGA segment if necessary.
        !           447:        //
        !           448:        if (y == fb_next_segment_y) {
        !           449:            fb =    this_segment + 
        !           450:                    ((y % fb_lines_per_segment) * fb_shorts_per_line) +
        !           451:                    fb_x_offset_shorts;
        !           452:            fb_segment++;
        !           453:            fb_next_segment_y += fb_lines_per_segment;
        !           454:            
        !           455:            [self setWriteSegment: fb_segment];
        !           456:            [self setReadSegment: fb_segment];
        !           457:        }
        !           458: 
        !           459:        if (doLeft) {
        !           460:            [self _readBpp4planar:fb toBpp2packed32:vramPtr];
        !           461:            *vramPtr = (*vramPtr&(~lmask))|(*savePtr++&lmask);
        !           462:            [self _writeBpp2packed32:vramPtr toBpp4planar:fb];
        !           463:        }
        !           464: 
        !           465:        if (doRight) {
        !           466:            if (!skew) {
        !           467:                savePtr++;
        !           468:            } else {
        !           469:                [self _readBpp4planar:(fb+1) toBpp2packed32:(vramPtr+1)];
        !           470:                *(vramPtr+1)=(*(vramPtr+1)&(~rmask))|(*savePtr++&rmask);
        !           471:                [self _writeBpp2packed32:(vramPtr+1) toBpp4planar:(fb+1)];
        !           472:            }
        !           473:        }
        !           474: 
        !           475:        //
        !           476:        // Advance fb (pointer into VGA framebuffer) one line.
        !           477:        //
        !           478:        fb += fb_shorts_per_line;
        !           479: 
        !           480:     }
        !           481: 
        !           482:     [self restorePlaneAndSegmentSettings];
        !           483: }
        !           484: 
        !           485: - (void)_displayCursor: (IODisplayInfo *)d shmem: (VGAShmem_t *)shmem
        !           486: // Description:        Private routine to display the cursor.  Sets up the
        !           487: //             cursor rect.
        !           488: {
        !           489:     Point hs;
        !           490:     hs = shmem->hotSpot[shmem->frame];
        !           491:     shmem->cursorRect.maxx =
        !           492:         (shmem->cursorRect.minx = (shmem->cursorLoc).x - hs.x) + 16;
        !           493:     shmem->cursorRect.maxy =
        !           494:         (shmem->cursorRect.miny = (shmem->cursorLoc).y - hs.y) + 16;
        !           495:     [self _VGADisplayCursor:d shmem:shmem];
        !           496:     shmem->oldCursorRect = shmem->cursorRect;
        !           497: }
        !           498: 
        !           499: - (void)_sysHideCursor: (IODisplayInfo *)d shmem: (VGAShmem_t *)shmem
        !           500: // Description:        Private routing to hide the cursor.
        !           501: {
        !           502:     if (!shmem->cursorShow++) {
        !           503:        [self _VGARemoveCursor:d shmem:shmem];
        !           504:     }
        !           505: }
        !           506: 
        !           507: - (void)_sysShowCursor: (IODisplayInfo *)d shmem: (VGAShmem_t *)shmem
        !           508: // Description:        Private routine to show the cursor
        !           509: {
        !           510:     if (shmem->cursorShow)
        !           511:        if (!--shmem->cursorShow)
        !           512:            [self _displayCursor:d shmem:shmem];
        !           513: }
        !           514: 
        !           515: - (void)_checkShield: (IODisplayInfo *)d shmem: (VGAShmem_t *)shmem
        !           516: // Description:        QUESTION
        !           517: {
        !           518:     Point hs;
        !           519:     int intersect;
        !           520:     Bounds tempRect;
        !           521:     
        !           522:     //
        !           523:     // Calculate temp cursorRect
        !           524:     //
        !           525:     hs = shmem->hotSpot[shmem->frame];
        !           526:     tempRect.maxx = (tempRect.minx = (shmem->cursorLoc).x - hs.x) + 16;
        !           527:     tempRect.maxy = (tempRect.miny = (shmem->cursorLoc).y - hs.y) + 16;
        !           528: 
        !           529:     intersect = RECTS_INTERSECT(tempRect, shmem->shieldRect);
        !           530:     if (intersect != shmem->shielded) {
        !           531:        (shmem->shielded = intersect) ? [self _sysHideCursor:d shmem:shmem] :
        !           532:                                        [self _sysShowCursor:d shmem:shmem];
        !           533:     }
        !           534: }
        !           535: 
        !           536: 
        !           537: static const char *
        !           538: find_parameter(const char *parameter, const char *string)
        !           539: // Description:        Find parameter in string and return what follows
        !           540: //             it.  E.g. for string = "Width: 10" and
        !           541: //             parameter = "Width:" return "10".
        !           542: {
        !           543:     int c;
        !           544:     size_t length;
        !           545: 
        !           546:     length = strlen(parameter);
        !           547:     while (*string != 0) {
        !           548:        if (strncmp(string, parameter, length) == 0) {
        !           549:            string += length;
        !           550:            while ((c = *string) != '\0' && (c == ' ' || c == '\t'))
        !           551:                string++;
        !           552:            return (c != 0) ? string : 0;
        !           553:        }
        !           554:        string++;
        !           555:     }
        !           556:     return 0;
        !           557: }
        !           558: 
        !           559: 
        !           560: - (void)_generateName: (char *)name andUnit:(IOObjectNumber *)unit
        !           561: // Description:        Used to generate a name for a new Display object.
        !           562: //              "name" is a char array of size IO_STRING_LENGTH
        !           563: {
        !           564:     static int nextSVGAUnit = 0;
        !           565: 
        !           566:     *unit = nextSVGAUnit++;
        !           567:     sprintf(name, "SVGADisplay%d", *unit);
        !           568: }
        !           569: 
        !           570: 
        !           571: //
        !           572: // END:                Implementation of private routines for SVGA
        !           573: //
        !           574: 
        !           575: 
        !           576: 
        !           577: //
        !           578: // BEGIN:      Implementation of the evScreen protocol
        !           579: //
        !           580: 
        !           581: 
        !           582: - hideCursor: (int)token
        !           583: {
        !           584:     SET_SEMAPHORE([self _shmem]);
        !           585:     [self _sysHideCursor:[self displayInfo] shmem:[self _shmem]];
        !           586:     CLEAR_SEMAPHORE([self _shmem]);
        !           587:     return self;
        !           588: }
        !           589: 
        !           590: - moveCursor:(Point*)cursorLoc frame:(int)frame token:(int)t
        !           591: {
        !           592:     VGAShmem_t *shmem;
        !           593:     
        !           594:     shmem = [self _shmem];
        !           595:     SET_SEMAPHORE(shmem);
        !           596:     shmem->frame = frame;
        !           597:     shmem->cursorLoc = *cursorLoc;
        !           598:     if (!shmem->cursorShow++) {
        !           599:        [self _VGARemoveCursor:[self displayInfo] shmem:shmem];
        !           600:     }
        !           601:     if (shmem->cursorObscured) {
        !           602:        shmem->cursorObscured = 0;
        !           603:        if (shmem->cursorShow)
        !           604:            --shmem->cursorShow;
        !           605:     }
        !           606:     if (shmem->shieldFlag) {
        !           607:        [self _checkShield:[self displayInfo] shmem:shmem];
        !           608:     }
        !           609:     if (shmem->cursorShow) {
        !           610:        if (!--shmem->cursorShow) {
        !           611:            [self _displayCursor:[self displayInfo] shmem:shmem];
        !           612:        }
        !           613:     }
        !           614:     CLEAR_SEMAPHORE(shmem);
        !           615:     return self;
        !           616: }
        !           617: 
        !           618: - showCursor:(Point*)cursorLoc frame:(int)frame token:(int)t
        !           619: {
        !           620:     VGAShmem_t *shmem;
        !           621:     
        !           622:     shmem = [self _shmem];
        !           623:     SET_SEMAPHORE(shmem);
        !           624:     shmem->frame = frame;
        !           625:     shmem->cursorLoc = *cursorLoc;
        !           626:     if (shmem->shieldFlag) {
        !           627:        [self _checkShield:[self displayInfo] shmem:shmem];
        !           628:     }
        !           629:     [self _sysShowCursor:[self displayInfo] shmem:shmem];
        !           630:     CLEAR_SEMAPHORE(shmem);
        !           631:     return self;
        !           632: }
        !           633: 
        !           634: //
        !           635: // END:                Implementation of the evScreen protocol
        !           636: //
        !           637: 
        !           638: 
        !           639: //
        !           640: // BEGIN:      EXPORTED methods
        !           641: //
        !           642: 
        !           643: - (void)setReadSegment: (unsigned char)segmentNum
        !           644: // Description:        Select which 64K segment we intend to read from -
        !           645: //             this must be overridden by a subclasser.
        !           646: {
        !           647: }
        !           648: 
        !           649: 
        !           650: - (void)setWriteSegment: (unsigned char)segmentNum
        !           651: // Description:        Select which 64K segment we intend to write from -
        !           652: //             this must be overridden by a subclasser.
        !           653: {
        !           654: }
        !           655: 
        !           656: 
        !           657: - (void)setReadPlane: (unsigned char)planeNum
        !           658: // Description:        Select which of 4 bit planes to read from in planar
        !           659: //             modes - only one plane can be active at a time.
        !           660: {
        !           661: }
        !           662: 
        !           663: 
        !           664: - (void)setWritePlane: (unsigned char)planeNum
        !           665: // Description:        Select one of 4 bit planes to write to in planar modes,
        !           666: //             although more than one plane can be active at a time,
        !           667: //             this routine only allows access to 1 plane at a time.
        !           668: {
        !           669: }
        !           670: 
        !           671: 
        !           672: - (void)savePlaneAndSegmentSettings
        !           673: // Description:        Save plane and segment settings.  These methods must
        !           674: //             be implemented by subclasses in a device specific way.
        !           675: {
        !           676: }
        !           677: 
        !           678: 
        !           679: - (void)restorePlaneAndSegmentSettings
        !           680: // Description:        Restore plane and segment settings.  These methods must
        !           681: //             be implemented by subclasses in a device specific way.
        !           682: {
        !           683: }
        !           684: 
        !           685: 
        !           686: - (void)enterSVGAMode
        !           687: // Description:        Put the display into SVGA mode. This typically happens
        !           688: //             when the window server starts running. This method is
        !           689: //             implemented by subclasses in a device specific way.
        !           690: {
        !           691: }
        !           692: 
        !           693: 
        !           694: - (void)revertToVGAMode
        !           695: // Description:        Get the device out of whatever advanced mode it was using
        !           696: //             and back into a state where it can be used as a standard
        !           697: //             VGA device. This method is implemented by subclasses in a
        !           698: //             device specific way.
        !           699: {
        !           700: }
        !           701: 
        !           702: 
        !           703: task_t (task_self)(void);      // from /NextDeveloper/Headers/mach/mach_traps.h
        !           704: 
        !           705: - (vm_address_t)mapFrameBufferAtPhysicalAddress:(unsigned int)addr
        !           706:        length:(int)length;
        !           707: // Description:        Look up the physical memory location for this device instance
        !           708: //             and map it into VM for use by the device driver. If problems
        !           709: //             occur, the method returns (vm_address_t)0. If addr is not 0,
        !           710: //             then it is used as the physical memory address and
        !           711: //             length is used as the length.
        !           712: {
        !           713:     vm_address_t       vmLocation;
        !           714:     IOReturn           result = IO_R_SUCCESS;
        !           715:     
        !           716:     if (addr != 0)     // Override configuration XXX BOGUS!!!
        !           717:     {
        !           718:        // This is totally bogus.  I cannot believe that it is
        !           719:        // public API.  NB: This mapping cannot be freed using
        !           720:        // unmapMemoryRange:from: in IOEISADirectDevice.
        !           721:        if (_KernBusMemoryCreateMapping(addr,
        !           722:                                    length,
        !           723:                                    &vmLocation,
        !           724:                                    current_task_EXTERNAL(),
        !           725:                                    YES,
        !           726:                                    IO_WriteThrough) != KERN_SUCCESS)
        !           727:                result = IO_R_NO_MEMORY;
        !           728:     }
        !           729:     else
        !           730:     {
        !           731:        result = [self  mapMemoryRange:0        //QUESTION--what is this???
        !           732:                        to:&vmLocation
        !           733:                        findSpace:YES
        !           734:                        cache:IO_WriteThrough];
        !           735:     }
        !           736: 
        !           737:     if (result != IO_R_SUCCESS)
        !           738:     {
        !           739:        IOLog("IOSVGADisplay/mapFrameBuffer: Can't map memory (%s)\n",
        !           740:            [self stringFromReturn:result]);
        !           741:        return (vm_address_t)0;
        !           742:     }
        !           743: 
        !           744:     return vmLocation;
        !           745: }
        !           746: 
        !           747: 
        !           748: 
        !           749: - (int)selectMode:(const IODisplayInfo *)modeList
        !           750:        count:(int)count
        !           751:        valid:(const BOOL *)isValid
        !           752: // Description:        Choose a mode from the list `modeList' (containing `count'
        !           753: //             modes) based on the value of the `DisplayMode' key in the
        !           754: //             device's config table.  If `isValid' is nonzero, each element
        !           755: //             specifies whether or not the corresponding mode is valid.
        !           756: {
        !           757:     const char *displayMode;
        !           758:     IOConfigTable *configTable;
        !           759:     int k, width, height;
        !           760:     int screenWidth, screenHeight, memorySize, ramdacSpeed;
        !           761:     int scanRate;
        !           762:     unsigned int modeUnavailableFlag;
        !           763:     IOBitsPerPixel bitsPerPixel;
        !           764:     IOColorSpace colorSpace;
        !           765:     int refreshRate;
        !           766:     const char *s;
        !           767: 
        !           768:     /* Get the string describing the display mode. */
        !           769: 
        !           770:     configTable = [[self deviceDescription] configTable];
        !           771:     if (configTable == nil)
        !           772:        return -1;
        !           773:     displayMode = [configTable valueForStringKey:"Display Mode"];
        !           774:     if (displayMode == 0) {
        !           775:        /* Historical: for 3.1 drivers only. */
        !           776:        displayMode = [configTable valueForStringKey:"DisplayMode"];
        !           777:        if (displayMode == 0)
        !           778:            return -1;
        !           779:     }
        !           780: 
        !           781:     /* Parse the string.  It should be of the form
        !           782:      *   Width:# Height:# ColorSpace:(BW:#|RGB:###/#) Refresh:# Hz
        !           783:      * where `Width' and `Height' specify the width and height of the
        !           784:      * framebuffer, `ColorSpace' specifies the color space for the
        !           785:      * framebuffer, and `Refresh' specifies the refresh rate in Hz.
        !           786:      * The color space parameter should be either BW followed by the
        !           787:      * bits/pixel, or RGB followed by the bits/component for each
        !           788:      * component followed by the bits/pixel.
        !           789:      *
        !           790:      * For example, here is the display mode specification for the
        !           791:      * RGB mode of the S3:
        !           792:      *   Width: 800 Height: 600 ColorSpace: RGB:555/16 Refresh: 60 Hz
        !           793:      */
        !           794: 
        !           795:     height = width = 0;
        !           796:     s = find_parameter("Width:", displayMode);
        !           797:     if (s != 0)        {
        !           798:        width = strtol(s, 0, 10);
        !           799:     }
        !           800:     
        !           801:     s = find_parameter("Height:", displayMode);
        !           802:     if (s != 0)        {
        !           803:        height = strtol(s, 0, 10);
        !           804:     }
        !           805: 
        !           806:     s = find_parameter("Refresh:", displayMode);
        !           807:     if (s == 0)
        !           808:        return -1;
        !           809:     refreshRate = strtol(s, 0, 10);
        !           810: 
        !           811:     s = find_parameter("ColorSpace:", displayMode);
        !           812:     if (s == 0)
        !           813:        return -1;
        !           814:     if (strncmp(s, "BW:2", 4) == 0) {
        !           815:         bitsPerPixel = IO_2BitsPerPixel;
        !           816:        colorSpace = IO_OneIsBlackColorSpace;
        !           817:     } else if (strncmp(s, "BW:8", 4) == 0) {
        !           818:         bitsPerPixel = IO_8BitsPerPixel;
        !           819:        colorSpace = IO_OneIsWhiteColorSpace;
        !           820:     } else if (strncmp(s, "RGB:256/8", 9) == 0) {
        !           821:         bitsPerPixel = IO_8BitsPerPixel;
        !           822:        colorSpace = IO_RGBColorSpace;
        !           823:     } else if (strncmp(s, "RGB:444/16", 10) == 0) {
        !           824:         bitsPerPixel = IO_12BitsPerPixel;
        !           825:        colorSpace = IO_RGBColorSpace;
        !           826:     } else if (strncmp(s, "RGB:555/16", 10) == 0) {
        !           827:         bitsPerPixel = IO_15BitsPerPixel;
        !           828:        colorSpace = IO_RGBColorSpace;
        !           829:     } else if (strncmp(s, "RGB:888/32", 10) == 0) {
        !           830:         bitsPerPixel = IO_24BitsPerPixel;
        !           831:        colorSpace = IO_RGBColorSpace;
        !           832:     } else {
        !           833:        return -1;
        !           834:     }
        !           835: 
        !           836: 
        !           837:     /*
        !           838:      * Now look for 4.0 style optional parameters. The display mode
        !           839:      * specification looks like "Resolution:1280x1024 Screen:1600x1200
        !           840:      * Refresh:60Hz ColorSpace:RGB:444/16 Memory:4MB RAMDAC:175Hz Sync:1000"; 
        !           841:      */
        !           842:      
        !           843:     s = find_parameter("Resolution:", displayMode);
        !           844:     if (s != 0)        {
        !           845:         char *end;
        !           846:        width = strtol(s, &end, 10);
        !           847:        height = strtol(end+1, 0, 10);
        !           848:     }
        !           849:     
        !           850:     if ((height == 0) || (width == 0))
        !           851:        return -1;
        !           852:        
        !           853:     s = find_parameter("Screen:", displayMode);
        !           854:     if (s != 0)        {
        !           855:         char *end;
        !           856:        screenWidth = strtol(s, &end, 10);
        !           857:        height = strtol(end+1, 0, 10);
        !           858:     } else {
        !           859:        screenWidth = width;
        !           860:        screenHeight = height;
        !           861:     }
        !           862: 
        !           863:     /* These parameters are not used by the superclass. */
        !           864:     s = find_parameter("Memory:", displayMode);
        !           865:     if (s != 0)        {
        !           866:        memorySize = strtol(s, 0, 10);
        !           867:     }
        !           868: 
        !           869:     s = find_parameter("RAMDAC:", displayMode);
        !           870:     if (s != 0)        {
        !           871:        ramdacSpeed = strtol(s, 0, 10);
        !           872:     }
        !           873: 
        !           874:     s = find_parameter("Sync:", displayMode);
        !           875:     if (s != 0)        {
        !           876:        scanRate = strtol(s, 0, 10);
        !           877:     }
        !           878: 
        !           879:     modeUnavailableFlag = 0;
        !           880:     s = find_parameter("Available:", displayMode);
        !           881:     if (s != 0)        {
        !           882:        modeUnavailableFlag = strtol(s, 0, 10);
        !           883:     }
        !           884:     
        !           885: 
        !           886:     /* Now try to match these parameters with the list of modes. */
        !           887:     for (k = 0; k < count; k++) {
        !           888:        if (isValid != 0 && !isValid[k])
        !           889:            continue;
        !           890:         if (modeUnavailableFlag != 0)
        !           891:             continue;
        !           892:        if (modeList[k].width == width
        !           893:            && modeList[k].height == height
        !           894:            && modeList[k].colorSpace == colorSpace
        !           895:            && modeList[k].bitsPerPixel == bitsPerPixel
        !           896:            && modeList[k].refreshRate == refreshRate) {
        !           897:            switch (bitsPerPixel) {
        !           898:            case IO_2BitsPerPixel:  s = "BW:2"; break;
        !           899:            case IO_8BitsPerPixel:
        !           900:                if (colorSpace == IO_RGBColorSpace) s = "RGB:256/8";
        !           901:                else                                s = "BW:8";
        !           902:                break;
        !           903:            case IO_12BitsPerPixel: s = "RGB:444/16"; break;
        !           904:            case IO_15BitsPerPixel: s = "RGB:555/16"; break;
        !           905:            case IO_24BitsPerPixel: s = "RGB:888/32"; break;
        !           906:            default:     s = "Unknown color space"; break;
        !           907:            }
        !           908:            IOLog("Display: Mode selected: %d x %d @ %d Hz (%s)\n",
        !           909:                width, height, refreshRate, s);
        !           910:            return k;
        !           911:        }
        !           912:     }
        !           913:     IOLog("Display: Requested mode is not available.\n");
        !           914:     return -1;
        !           915: }
        !           916: 
        !           917: 
        !           918: - (int)selectMode: (const IODisplayInfo *)modeList count:(int)count
        !           919: // Description:        Equivalent to the above with `isValid' set to zero.
        !           920: {
        !           921:     return [self selectMode:modeList count:count valid:0];
        !           922: }
        !           923: 
        !           924: 
        !           925: + (BOOL)probe:deviceDescription
        !           926: // Description:        Create an instance of subclass to be associated with
        !           927: //             specified deviceDescription. Returns whether or not
        !           928: //             successful.
        !           929: {
        !           930:     IOSVGADisplay *inst;
        !           931: 
        !           932:     // Create an instance and initialize some basic instance variables.
        !           933:     inst = [[self alloc] initFromDeviceDescription:deviceDescription];
        !           934:     if (inst == nil) {
        !           935:        return NO;
        !           936:     }
        !           937:     
        !           938:     [inst setDeviceKind:"frame buffer"];
        !           939: 
        !           940:     [inst registerDevice];
        !           941: 
        !           942:     return YES;
        !           943: }
        !           944: 
        !           945: 
        !           946: 
        !           947: 
        !           948: - initFromDeviceDescription:deviceDescription
        !           949: // Description:        Initialize per specified deviceDescription. Returns
        !           950: //             nil on error
        !           951: {
        !           952:     char name[IO_STRING_LENGTH];
        !           953:     IOObjectNumber unit;
        !           954:     
        !           955:     if ([super initFromDeviceDescription:deviceDescription] == nil) {
        !           956:        return [super free];
        !           957:     }
        !           958: 
        !           959:     [self _generateName:name andUnit:&unit];
        !           960:     [self setUnit:unit];
        !           961:     [self setName:name];
        !           962:     return self;
        !           963: }
        !           964: 
        !           965: 
        !           966: 
        !           967: - setBrightness:(int)level token:(int)t
        !           968: // Description:        Setting the brighness is a device-specific operation
        !           969: //             which must be implemented by a subclass.  This just
        !           970: //             checks if a legal level was sent.
        !           971: {
        !           972:     if ( level < EV_SCREEN_MIN_BRIGHTNESS
        !           973:        || level > EV_SCREEN_MAX_BRIGHTNESS )
        !           974:     {
        !           975:        IOLog("%s: Invalid arg to setBrightness:%d\n",
        !           976:            [self name], level );
        !           977:     }
        !           978:     return self;
        !           979: }
        !           980: 
        !           981: - (IOReturn)getIntValues:(unsigned *)parameterArray
        !           982:        forParameter:(IOParameterName)parameterName
        !           983:        count:(unsigned int *)count
        !           984: // Description:        Get and set parameters. These include support
        !           985: //             for getting the frame buffer parameters, registering it
        !           986: //             with the event system, returning the registration token.
        !           987: {
        !           988:     unsigned int fb_dimensions[VGA_FB_DIMENSIONS_SIZE];
        !           989:     IOReturn r;
        !           990:     int i;
        !           991:     unsigned *returnedCount = count;
        !           992:     unsigned maxCount = *count;
        !           993: 
        !           994:     if ( strcmp(parameterName, VGA_FB_MAP) == 0 )
        !           995:     {
        !           996:         parameterArray[0] = 0;
        !           997:        [self enterSVGAMode];
        !           998:        [kmId registerDisplay:self];
        !           999:        *returnedCount = 1;
        !          1000:        return IO_R_SUCCESS;
        !          1001:     }
        !          1002:     else if ( strcmp(parameterName, VGA_FB_DIMENSIONS) == 0 )
        !          1003:     {
        !          1004:         IODisplayInfo *display = [self displayInfo];
        !          1005:        
        !          1006:        fb_dimensions[VGA_FB_WIDTH] = display->width;
        !          1007:        fb_dimensions[VGA_FB_HEIGHT] = display->height;
        !          1008:        fb_dimensions[VGA_FB_ROWBYTES] = display->rowBytes;
        !          1009: 
        !          1010:        *returnedCount = 0;
        !          1011:        for( i=0; i<VGA_FB_DIMENSIONS_SIZE; i++) {
        !          1012:            if (*returnedCount == maxCount)
        !          1013:                break;
        !          1014:            parameterArray[i] = fb_dimensions[i];
        !          1015:            (*returnedCount)++;
        !          1016:        }
        !          1017:        return IO_R_SUCCESS;
        !          1018: 
        !          1019:     }
        !          1020:     else if ( strcmp(parameterName, VGA_FB_REGISTER) == 0 )
        !          1021:     {
        !          1022:        r = [self _registerWithED];
        !          1023:        *returnedCount = 0;
        !          1024:        if ( maxCount > 0 )
        !          1025:        {
        !          1026:            *returnedCount = 1;
        !          1027:            parameterArray[0] = [self token];
        !          1028:        }
        !          1029:        return r;
        !          1030:     }
        !          1031:     else
        !          1032:     {
        !          1033:        r = [super getIntValues:parameterArray
        !          1034:                        forParameter:parameterName
        !          1035:                        count:returnedCount];
        !          1036:        return r;
        !          1037:     }
        !          1038: }
        !          1039: 
        !          1040:                
        !          1041: - (IOReturn)setIntValues:(unsigned *)parameterArray
        !          1042:        forParameter:(IOParameterName)parameterName
        !          1043:        count:(unsigned int)count
        !          1044: // Description:        Set parameters. This can be used to unregister the frame
        !          1045: //             buffer as well as set the transfer function.
        !          1046: {
        !          1047:     if ( strcmp(parameterName, VGA_FB_UNMAP) == 0 ) {
        !          1048:         // [self _unmap];
        !          1049:        [self revertToVGAMode];
        !          1050:        return IO_R_SUCCESS;    
        !          1051:     } else if ( strcmp(parameterName, VGA_FB_UNREGISTER) == 0 ) {
        !          1052:        if ( count != 1 )
        !          1053:            return IO_R_INVALID_ARG;
        !          1054:        [[EventDriver instance] unregisterScreen:parameterArray[0]];
        !          1055:        return IO_R_SUCCESS;
        !          1056:        
        !          1057:     } else {
        !          1058:        return [super setIntValues:parameterArray
        !          1059:                      forParameter:parameterName
        !          1060:                      count:count];
        !          1061:     }
        !          1062: }
        !          1063: 
        !          1064: - (IOConsoleInfo *)allocateConsoleInfo;
        !          1065: // Description:        Allocates a console support info structure based on this
        !          1066: //             display. This structure, and the functions in it, are used
        !          1067: //             to display alert and console windows.
        !          1068: {
        !          1069:     return SVGAAllocateConsole([self displayInfo]);
        !          1070: }
        !          1071: 
        !          1072: //
        !          1073: // END:                EXPORTED methods
        !          1074: //
        !          1075: 
        !          1076: @end

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.