Annotation of researchv9/sys/sundev/bwtwo.c, revision 1.1.1.1

1.1       root        1: #ifndef lint
                      2: static  char sccsid[] = "@(#)bwtwo.c 1.1 86/02/03 Copyr 1985 Sun Micro";
                      3: #endif
                      4: 
                      5: /*
                      6:  * Copyright (c) 1986 by Sun Microsystems, Inc.
                      7:  */
                      8: 
                      9: /*
                     10:  * Sun Two Black & White Board(s) Driver
                     11:  */
                     12: 
                     13: #include "bwtwo.h"
                     14: 
                     15: #include "../h/param.h"
                     16: #include "../h/systm.h"
                     17: #include "../h/dir.h"
                     18: #include "../h/user.h"
                     19: #include "../h/proc.h"
                     20: #include "../h/buf.h"
                     21: #include "../h/conf.h"
                     22: #include "../h/file.h"
                     23: #include "../h/map.h"
                     24: #include "../h/vmmac.h"
                     25: 
                     26: #include "../sun/fbio.h"
                     27: 
                     28: #include "../machine/pte.h"
                     29: #include "../machine/mmu.h"
                     30: #include "../machine/cpu.h"
                     31: 
                     32: #include "../sundev/mbvar.h"
                     33: #include "../sundev/bw2reg.h"
                     34: 
                     35: #ifdef sun3
                     36: #include "../sun3/eeprom.h"
                     37: #endif sun3
                     38: 
                     39: extern char    CADDR1[];
                     40: 
                     41: int    copyenpfnum;    /* pfnum before shadow memory mapped in */
                     42: caddr_t        copyenvirt = 0; /* virtual address mapped to shadow memory */
                     43: 
                     44: struct bw2_softc {
                     45:        caddr_t image;
                     46: } bw2_softc[NBWTWO];
                     47: 
                     48: #define        BW2SIZEX        1152
                     49: #define        BW2SIZEY        900
                     50: #define        BW2SQUARESIZEX  1024
                     51: #define        BW2SQUARESIZEY  1024
                     52: 
                     53: /*
                     54:  * Driver information for auto-configuration stuff.
                     55:  */
                     56: int    bwtwoprobe(), bwtwoattach(), bwtwointr();
                     57: struct mb_device *bwtwoinfo[NBWTWO];
                     58: struct mb_driver bwtwodriver = {
                     59:        bwtwoprobe, 0, bwtwoattach, 0, 0, bwtwointr,
                     60:        sizeof (struct bw2dev) + CLBYTES /* XXX */, "bwtwo", bwtwoinfo, 0, 0, 0,
                     61: };
                     62: 
                     63: /*
                     64:  * Only allow opens for writing or reading and writing
                     65:  * because reading is nonsensical.
                     66:  */
                     67: bwtwoopen(dev, flag)
                     68:        dev_t dev;
                     69: {
                     70: 
                     71:        fbopen(dev, flag, NBWTWO, bwtwoinfo);
                     72: }
                     73: 
                     74: bwtwoclose(dev, flag)
                     75:        dev_t dev;
                     76: {
                     77: }
                     78: 
                     79: /*ARGSUSED*/
                     80: bwtwommap(dev, off, prot)
                     81:        dev_t dev;
                     82:        off_t off;
                     83:        int prot;
                     84: {
                     85:        register caddr_t hold;
                     86:        register int unit = minor(dev);
                     87:        int page;
                     88: 
                     89:        hold = bwtwoinfo[unit]->md_addr;
                     90:        bwtwoinfo[unit]->md_addr = bw2_softc[unit].image;
                     91:        page = fbmmap(dev, off, prot, NBWTWO, bwtwoinfo, BW2_FBSIZE);
                     92:        bwtwoinfo[unit]->md_addr = hold;
                     93:        return (page);
                     94: }
                     95: 
                     96: /*
                     97:  * Determine if a bwtwo exists at the given address.
                     98:  */
                     99: /*ARGSUSED*/
                    100: bwtwoprobe(reg, unit)
                    101:        caddr_t reg;
                    102:        int     unit;
                    103: {
                    104: #ifdef sun3
                    105:        /* 
                    106:         * For the sun3 we have to rely on the machine type since the bits 
                    107:         * in the enable register may not be reliable.
                    108:         */
                    109:        int result;
                    110: 
                    111:        /*
                    112:         * XXX - kludge used to get around current mem_rop bug.
                    113:         * We need to have the page before the frame buffer to not have
                    114:         * have any "holes" in them as the mem_rop code will sometimes
                    115:         * access this page.  We kludge here to avoid this problem by
                    116:         * increasing the size of area to be mapped by adding CLBYTES
                    117:         * to the device size mapped by the autoconfig code.  Here
                    118:         * we remap all but the first page so that the first page map
                    119:         * entry is duplicated and then we bump the virtual address
                    120:         * up by CLBYTES in bwtwoattach().
                    121:         */
                    122:        mapin(&Sysmap[btoc(reg + CLBYTES - KERNELBASE)],
                    123:            (u_int)btoc(reg + CLBYTES),
                    124:            ((*(u_int *)&Sysmap[btoc(reg - KERNELBASE)]) & PG_PFNUM),
                    125:            btoc(BW2_FBSIZE), PG_V | PG_KW);
                    126: 
                    127:        switch (cpu) {
                    128:        case CPU_SUN3_160:
                    129:                result = BW2_FBSIZE;
                    130:                break;
                    131:        case CPU_SUN3_50:
                    132:                result = BW2_FBSIZE;
                    133:                break;
                    134:        case CPU_SUN3_260:
                    135:                result = 0;
                    136:                break;
                    137:        default:
                    138:                result = 0;
                    139:                break;
                    140:        }
                    141:        return (result);
                    142: #endif sun3
                    143: #ifdef sun2
                    144:        struct  bw2dev *bw2dev = (struct bw2dev *)(reg + CLBYTES); /* XXX */
                    145:        register struct bw2cr *alias1;
                    146:        register struct bw2cr *alias2;
                    147:        short   w1;
                    148:        register short  w2, wrestore;
                    149:        int     result = 0;
                    150: 
                    151:        /*
                    152:         * XXX - kludge used to get around current mem_rop bug.
                    153:         * We need to have the page before the frame buffer to not have
                    154:         * have any "holes" in them as the mem_rop code will sometimes
                    155:         * access this page.  We kludge here to avoid this problem by
                    156:         * increasing the size of area to be mapped by adding CLBYTES
                    157:         * to the device size mapped by the autoconfig code.  Here
                    158:         * we remap all but the first page so that the first page map
                    159:         * entry is duplicated and then we bump the virtual address
                    160:         * up by CLBYTES above for bw2dev and in bwtwoattach().
                    161:         */
                    162:        mapin(&Sysmap[btoc(reg + CLBYTES - KERNELBASE)],
                    163:            (u_int)btoc(reg + CLBYTES),
                    164:            ((*(u_int *)&Sysmap[btoc(reg - KERNELBASE)]) & PG_PFNUM),
                    165:            btoc(BW2_FBSIZE), PG_V | PG_KW);
                    166: 
                    167:        bw2crmapin(bw2dev);
                    168:        alias1 = &bw2dev->bw2cr;
                    169:        alias2 = alias1 + 1;
                    170: 
                    171:        /*
                    172:         * Two adjacent shorts should be the same because
                    173:         * the control register is replicated every 2 bytes
                    174:         * throughout the control page.
                    175:         */
                    176:        if ((w1 = peek((short *)alias1)) == -1)
                    177:                return (0);
                    178:        wrestore = w1;
                    179:        ((struct bw2cr *)&w1)->vc_copybase = 0xAA & BW2_COPYBASEMASK;
                    180:        if (poke((short *)alias1, w1))
                    181:                return (0);
                    182:        if ((w2 = peek((short *)alias2)) == -1)
                    183:                goto restore;
                    184:        if (w1 != w2)
                    185:                goto restore;
                    186:        ((struct bw2cr *)&w1)->vc_copybase = ~0xAA & BW2_COPYBASEMASK;
                    187:        if (poke((short *)alias1, w1))
                    188:                goto restore;
                    189:        if ((w2 = peek((short *)alias2)) == -1)
                    190:                goto restore;
                    191:        if (w1 != w2)
                    192:                goto restore;
                    193:        result = BW2_FBSIZE;
                    194: restore:
                    195:        if (poke((short *)alias1, wrestore))
                    196:                panic("bwtwoprobe");
                    197:        return (result);
                    198: #endif sun2
                    199: }
                    200: 
                    201: /*
                    202:  * Set up the softc structure
                    203:  */
                    204: bwtwoattach(md)
                    205: register struct mb_device *md;
                    206: {
                    207: #ifdef sun2
                    208:        register struct bw2dev *bw2dev;
                    209: #endif
                    210:        int     pfnum;
                    211:        caddr_t fbvirtaddr;
                    212:        caddr_t v;
                    213:        int     i;
                    214: 
                    215:        /*
                    216:         * XXX - Last part of mem_rop bug kludge, increase the virtual
                    217:         * address set up by autoconfig by CLBYTES as we have remapped
                    218:         * the first page to be a duplicate in bwtwoprobe().
                    219:         */
                    220:        md->md_addr += CLBYTES;
                    221: 
                    222:        pfnum = getkpgmap(md->md_addr) & PG_PFNUM;
                    223: #ifdef sun3
                    224:        /*
                    225:         * If we are on a SUN3_50 (Model 25), then we must
                    226:         * reserve the on board memory for the frame buffer.
                    227:         */
                    228:        if (cpu == CPU_SUN3_50) {
                    229:                if (fbobmemavail == 0)
                    230:                        panic("No video memory");
                    231:                else
                    232:                        fbobmemavail = 0;
                    233:        }
                    234: #endif sun3
                    235: 
                    236:        /*
                    237:         * Have we passed this way before? 
                    238:         */
                    239:        if (fbobmemavail == 0) {
                    240:                if (copyenvirt == 0) {
                    241:                        copyenvirt = (caddr_t)(*romp->v_fbaddr);
                    242:                        if (pfnum == copyenpfnum)
                    243:                                bw2_softc[md->md_unit].image = copyenvirt;
                    244:                        else
                    245:                                bw2_softc[md->md_unit].image = md->md_addr;
                    246:                }
                    247:                return;
                    248:        }
                    249: 
                    250:        /* 
                    251:         * We know that the copy memory can be used.  Use the
                    252:         * shadow memory if the config flags say to use it.
                    253:         */
                    254:        if ((md->md_flags & BW2_USECOPYMEM) == 0) {
                    255:                /* don't bother using reserved shadow memory */
                    256:                copyenvirt  = md->md_addr;
                    257:                bw2_softc[md->md_unit].image = md->md_addr;
                    258:                return;
                    259:        }
                    260: 
                    261:        /*
                    262:         * Mark the onboard frame buffer memory as not available
                    263:         * anymore as we are going to use it for copy memory.
                    264:         */
                    265:        fbobmemavail = 0;
                    266: 
                    267:        if (*romp->v_outsink != OUTSCREEN || *romp->v_fbtype != FBTYPE_SUN2BW)
                    268:                fbvirtaddr = (caddr_t)md->md_addr;
                    269:        else {
                    270:                rmfree(kernelmap, (long)btoc(BW2_FBSIZE), 
                    271:                          btokmx((struct pte *)(md->md_addr)));
                    272:                mapout(&Usrptmap[btokmx((struct pte *)(md->md_addr))], 
                    273:                          btoc(BW2_FBSIZE));
                    274:                fbvirtaddr = (caddr_t)(*romp->v_fbaddr);
                    275:        } 
                    276:        copyenvirt = fbvirtaddr;
                    277:        copyenpfnum = getkpgmap(fbvirtaddr) & PG_PFNUM;
                    278: 
                    279:        /*
                    280:         * Copy the current frame buffer memory
                    281:         * to the copy memory as we map it in.
                    282:         */
                    283:        for (v = (caddr_t)fbvirtaddr, i = btop(OBFBADDR);
                    284:            i < btop(OBFBADDR + BW2_FBSIZE); v += NBPG, i++) {
                    285:                mapin(CMAP1, btop(CADDR1),
                    286:                    (u_int)(i | PGT_OBMEM), 1, PG_V | PG_KW);
                    287:                bcopy(v, CADDR1, NBPG);
                    288:                setpgmap(v, (long)(PG_V|PG_KW|PGT_OBMEM|i));
                    289:        }
                    290: 
                    291: #ifdef sun2
                    292:        bw2dev = (struct bw2dev *)md->md_addr;
                    293:        i = (OBFBADDR>>BW2_COPYSHIFT) | BW2_COPYENABLEMASK;
                    294:        (void) bwtwosetcr(&bw2dev->bw2cr, i, 1);
                    295: #endif sun2
                    296: #ifdef sun3
                    297:        setcopyenable();
                    298: #endif
                    299:        if (pfnum == copyenpfnum)
                    300:                bw2_softc[md->md_unit].image = copyenvirt;
                    301:        else
                    302:                bw2_softc[md->md_unit].image = md->md_addr;
                    303: }
                    304: 
                    305: /*ARGSUSED*/
                    306: bwtwoioctl(dev, cmd, data, flag)
                    307:        dev_t dev;
                    308:        caddr_t data;
                    309: {
                    310:        register int unit = minor(dev);
                    311: 
                    312:        switch (cmd) {
                    313: 
                    314:        case FBIOGTYPE: {
                    315:                register struct fbtype *fb = (struct fbtype *)data;
                    316: #ifdef sun2
                    317:                register struct bw2dev *bw2dev =
                    318:                    (struct bw2dev *)bwtwoinfo[unit]->md_addr;
                    319: #endif
                    320:                fb->fb_type = FBTYPE_SUN2BW;
                    321:                fb->fb_depth = 1;
                    322:                fb->fb_cmsize = 2;
                    323:                fb->fb_size = BW2_FBSIZE;
                    324: #ifdef sun3
                    325:                /*
                    326:                 * Look at the eeprom for screen configuration,
                    327:                 * if unknown default to standard sizes.
                    328:                 */
                    329:                switch (EEPROM->ee_diag.eed_scrsize) {
                    330:                case EED_SCR_1024X1024:
                    331:                        fb->fb_height = BW2SQUARESIZEY;
                    332:                        fb->fb_width = BW2SQUARESIZEX;
                    333:                        break;
                    334: 
                    335:                case EED_SCR_1152X900:
                    336:                default:
                    337:                        fb->fb_height = BW2SIZEY;
                    338:                        fb->fb_width = BW2SIZEX;
                    339:                        break;
                    340:                }
                    341: #endif sun3
                    342: #ifdef sun2
                    343:                /*
                    344:                 * Check for "square screen" jumper
                    345:                 */
                    346:                if (cpu != CPU_SUN2_120 && bwtwoinfo[unit]->md_unit == 0 &&
                    347:                    bw2dev->bw2cr.vc_1024_jumper) {
                    348:                        fb->fb_height = BW2SQUARESIZEY;
                    349:                        fb->fb_width = BW2SQUARESIZEX;
                    350:                } else {
                    351:                        fb->fb_height = BW2SIZEY;
                    352:                        fb->fb_width = BW2SIZEX;
                    353:                }
                    354: #endif sun2
                    355:                break;
                    356:                }
                    357: 
                    358:        default:
                    359:                u.u_error = ENOTTY;
                    360:        }
                    361: }
                    362: 
                    363: bwtwointr()
                    364: {
                    365:        int bwtwointclear();
                    366: 
                    367:        return (fbintr(NBWTWO, bwtwoinfo, bwtwointclear));
                    368: }
                    369: 
                    370: /*
                    371:  * Turn off interrupts on bwtwo board.
                    372:  */
                    373: #ifdef sun3
                    374: /*ARGSUSED*/
                    375: bwtwointclear(bw2dev)
                    376:        struct  bw2dev *bw2dev;
                    377: {
                    378: 
                    379:        (void) setintrenable(0);
                    380:        return (0);
                    381: }
                    382: #endif sun3
                    383: 
                    384: #ifdef sun2
                    385: bwtwointclear(bw2dev)
                    386:        struct  bw2dev *bw2dev;
                    387: {
                    388:        int     int_active;
                    389: 
                    390:        int_active = bw2dev->bw2cr.vc_int;
                    391:        (void) setintrenable(&bw2dev->bw2cr);
                    392:        return (int_active);
                    393: }
                    394: 
                    395: setvideoenable(bw2cr)
                    396:        struct bw2cr *bw2cr;
                    397: {
                    398: 
                    399:        bwtwosetcr(bw2cr, BW2_VIDEOENABLEMASK, 1);
                    400: }
                    401: 
                    402: setintrenable(bw2cr)
                    403:        struct bw2cr *bw2cr;
                    404: {
                    405: 
                    406:        bwtwosetcr(bw2cr, BW2_INTENABLEMASK, 0);
                    407: }
                    408: 
                    409: /*
                    410:  * Special access approach to video ctrl register needed because byte writes,
                    411:  * generated when do bit writes, replicates itself on the subsequent byte as
                    412:  * well (this is a hardware bug).  Thus, we need to access the register as a
                    413:  * word.  Also these routines assume that only one bit changes at a time.
                    414:  */
                    415: bwtwosetcr(bw2cr, mask, value)
                    416:        struct  bw2cr *bw2cr;
                    417:        short   mask;
                    418:        int     value;
                    419: {
                    420:        register short  w;
                    421: 
                    422:        /*
                    423:         * Read word from video control register.
                    424:         */
                    425:        w = *((short *)bw2cr);
                    426:        /*
                    427:         * Modify bit as requested.
                    428:         */
                    429:        if (value)
                    430:                w |= mask;
                    431:        else
                    432:                w &= ~mask;
                    433:        /*
                    434:         * Write word back to video control register.
                    435:         */
                    436:        *((short *)bw2cr) = w;
                    437:        return;
                    438: }
                    439: #endif sun2
                    440: 
                    441: #ifndef sun3
                    442: /*
                    443:  * Given the video base virtual address,
                    444:  * map in the control register address.
                    445:  * This lets us handle minor implementation differences.
                    446:  */
                    447: bw2crmapin(bw2dev)
                    448:        struct bw2dev *bw2dev;
                    449: {
                    450:        struct bw2cr *bw2cr = &bw2dev->bw2cr;
                    451:        int pte = getkpgmap((caddr_t)bw2dev);
                    452:        int page, delta;
                    453: 
                    454:        page = pte & PGT_MASK;
                    455: 
                    456:        if (page == PGT_OBMEM)
                    457:                delta = (int)BW2MB_CR - (int)BW2MB_FB;
                    458:        else if (page == PGT_OBIO)
                    459:                delta = (int)BW2VME_CR - (int)BW2VME_FB;
                    460:        else
                    461:                panic("bwtwocraddr");
                    462: 
                    463:        mapin(&Sysmap[btoc((u_int)bw2cr - KERNELBASE)], btoc(bw2cr),
                    464:            pte + btoc(delta), 1, PG_V | (pte & PG_PROT));
                    465: }
                    466: #endif !sun3

unix.superglobalmegacorp.com

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