⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 neomagic.c

📁 这是一个同样来自贝尔实验室的和UNIX有着渊源的操作系统, 其简洁的设计和实现易于我们学习和理解
💻 C
字号:
#include <u.h>#include <libc.h>#include <bio.h>#include "pci.h"#include "vga.h"typedef struct {	Pcidev*	pci;	int	x;	int	y;} Neomagic;enum {	ExtCrtx = 0x19,	MaxCRT=0x85,	MaxGR=0xc7,};enum {	GeneralLockReg = 0x0A,	ExtCRTDispAddr = 0x0E,	ExtCRTOffset = 0x0F,	SysIfaceCntl1 = 0x10,	SysIfaceCntl2 = 0x11,	SingleAddrPage = 0x15,		/* not changed? */	DualAddrPage = 0x16,		/* not changed? */	PanelDispCntlReg1 = 0x20,	PanelDispCntlReg2 = 0x25,	PanelDispCntlReg3 = 0x30,	PanelVertCenterReg1 = 0x28,	PanelVertCenterReg2 = 0x29,	PanelVertCenterReg3 = 0x2A,	PanelVertCenterReg4 = 0x32,	/* not 2070 */	PanelHorizCenterReg1 = 0x33,	PanelHorizCenterReg2 = 0x34,	PanelHorizCenterReg3 = 0x35,	PanelHorizCenterReg4 = 0x36,	/* 2160, 2200, 2360 */	PanelVertCenterReg5 = 0x37,	/* 2200, 2360 */	PanelHorizCenterReg5 = 0x38,	/* 2200, 2360 */	ExtColorModeSelect = 0x90,	VerticalExt = 0x70,		/* 2200; iobase+4 */};static int crts[] = {	0x1D, 0x1F, 0x21, 0x23, 0x25, 0x2F,	/* also 40-59, 60-69, 70-MaxCRT */	-1};/* * Neomagic driver (fake) */static voidsnarf(Vga* vga, Ctlr* ctlr){	int i;	Pcidev *p;	Neomagic *nm;	generic.snarf(vga, ctlr);	outportw(Grx, 0x2609);	/* unlock neo registers */	outportw(Grx, 0x0015);	/* reset bank */	for(i=0; crts[i] >= 0; i++)		vga->crt[crts[i]] = vgaxi(Crtx, crts[i]);	for(i=0x40; i <= MaxCRT; i++)		vga->crt[i] = vgaxi(Crtx, i);	for(i=0x08; i<=0x3F; i++)		vga->graphics[i] = vgaxi(Grx, i);	for(i=0x70; i<=MaxGR; i++)		vga->graphics[i] = vgaxi(Grx, i);	if(vga->private == nil){		vga->private = alloc(sizeof(Neomagic));		nm = vga->private;		if((p = pcimatch(0, 0x10C8, 0)) == nil)			error("%s: not found\n", ctlr->name);		switch(p->did){		case 0x0003:			/* MagicGraph 128 ZV */			vga->f[1] = 80000000;			vga->vmz = 2048*1024;			vga->apz = 4*1024*1024;			break;		case 0x0083:			/* MagicGraph 128 ZV+ */			vga->f[1] = 80000000;			vga->vmz = 2048*1024;			vga->apz = 4*1024*1024;			break;		case 0x0004:			/* MagicGraph 128 XD */			vga->f[1] = 90000000;			vga->vmz = 2048*1024;			vga->apz = 16*1024*1024;			break;		case 0x0005:			/* MagicMedia 256 AV */			vga->f[1] = 110000000;			vga->vmz = 2560*1024;			vga->apz = 16*1024*1024;			break;		case 0x0006:			/* MagicMedia 256 ZX */			vga->f[1] = 110000000;			vga->vmz = 4096*1024;			vga->apz = 16*1024*1024;			break;		case 0x0001:			/* MagicGraph 128 */		case 0x0002:			/* MagicGraph 128 V */		default:			error("%s: DID %4.4uX unsupported\n",				ctlr->name, p->did);		}		nm->pci = p;	}	ctlr->flag |= Fsnarf;}static voidoptions(Vga*, Ctlr* ctlr){	ctlr->flag |= Ulinear|Hlinear|Foptions;}static voidinit(Vga* vga, Ctlr* ctlr){	Neomagic *nm;	int i, h, v, t;	generic.init(vga, ctlr);	nm = vga->private;	switch((vga->graphics[0x20]>>3)&3){	case 0:		nm->x = 640;		nm->y = 480;		break;	case 1:		nm->x = 800;		nm->y = 600;		break;	case 2:		nm->x = 1024;		nm->y = 768;	case 3:		nm->x = 1280;		nm->y = 1024;		break;	}	vga->crt[0x0C] = 0;	/* vga starting address (offset) */	vga->crt[0x0D] = 0;	vga->graphics[GeneralLockReg] = 0x01;	/* (internal or simultaneous) */	vga->attribute[0x10] &= ~0x40;	/* 2x4 mode not right for neomagic */	t = 2;		/* LCD only (0x01 for external) */	switch(vga->mode->x){	case 1280:		t |= 0x60;		break;	case 1024:		t |= 0x40;		break;	case 800:		t |= 0x20;		break;	}	if(0 && (nm->pci->did == 0x0005) || (nm->pci->did == 0x0006)){		vga->graphics[PanelDispCntlReg1] &= 0x98;		vga->graphics[PanelDispCntlReg1] |= (t & ~0x98);	}	else{		vga->graphics[PanelDispCntlReg1] &= 0xDC;	/* save bits 7:6, 4:2 */		vga->graphics[PanelDispCntlReg1] |= (t & ~0xDC);	}	vga->graphics[PanelDispCntlReg2] &= 0x38;	vga->graphics[PanelDispCntlReg3] &= 0xEF;	vga->graphics[PanelVertCenterReg1] = 0x00;	vga->graphics[PanelVertCenterReg2] = 0x00;	vga->graphics[PanelVertCenterReg3] = 0x00;	vga->graphics[PanelVertCenterReg4] = 0x00;	vga->graphics[PanelVertCenterReg5] = 0x00;	vga->graphics[PanelHorizCenterReg1] = 0x00;	vga->graphics[PanelHorizCenterReg2] = 0x00;	vga->graphics[PanelHorizCenterReg3] = 0x00;	vga->graphics[PanelHorizCenterReg4] = 0x00;	vga->graphics[PanelHorizCenterReg5] = 0x00;	if(vga->mode->x < nm->x){		vga->graphics[PanelDispCntlReg2] |= 0x01;		vga->graphics[PanelDispCntlReg3] |= 0x10;		h = ((nm->x - vga->mode->x) >> 4) - 1;		v = ((nm->y - vga->mode->y) >> 1) - 2;		switch(vga->mode->x){		case 640:			vga->graphics[PanelHorizCenterReg1] = h;			vga->graphics[PanelVertCenterReg3] = v;			break;		case 800:			vga->graphics[PanelHorizCenterReg2] = h;			vga->graphics[PanelVertCenterReg4] = v;			break;		case 1024:			vga->graphics[PanelHorizCenterReg5] = h;			vga->graphics[PanelVertCenterReg5] = v;			break;		}	}	vga->graphics[ExtCRTDispAddr] = 0x10;	vga->graphics[SysIfaceCntl1] &= 0x0F;	vga->graphics[SysIfaceCntl1] |= 0x30;	vga->graphics[SysIfaceCntl2] = 0x40;	/* make sure MMIO is enabled */	vga->graphics[SingleAddrPage] = 0x00;	vga->graphics[DualAddrPage] = 0x00;	vga->graphics[ExtCRTOffset] = 0x00;	t = vga->graphics[ExtColorModeSelect] & 0x70;	/* colour mode extension */	if(vga->mode->z == 8){		t |= 0x11;		vga->crt[0x13] = vga->mode->x/8;		vga->graphics[ExtCRTOffset] = vga->mode->x>>11;		vga->graphics[0x05] = 0x00;	/* linear addressing? */		vga->crt[0x14] = 0x40;	/* double word mode but don't count by 4 */	}	else if(vga->mode->z == 16){		t |= 0x13;		vga->crt[0x13] = vga->mode->x/4;		vga->graphics[0x05] = 0x00;	/* linear addressing? */		vga->crt[0x14] = 0x40;	/* double word mode but don't count by 4 */		vga->graphics[ExtCRTOffset] = vga->mode->x>>10;		for(i = 0; i < Pcolours; i++){			vga->palette[i][Red] = i<<1;			vga->palette[i][Green] = i;			vga->palette[i][Blue] = i<<1;		}	}	else if(vga->mode->z == 24){		t |= 0x14;		vga->crt[0x13] = (vga->mode->x*3)/8;//		vga->graphics[0x05] = 0x00;	/* linear addressing? */		vga->crt[0x14] = 0x40;	/* double word mode but don't count by 4 */		vga->graphics[ExtCRTOffset] = (vga->mode->x*3)>>11;		for(i = 0; i < Pcolours; i++){			vga->palette[i][Red] = i;			vga->palette[i][Green] = i;			vga->palette[i][Blue] = i;		}	}	else		error("depth %d not supported\n", vga->mode->z);	vga->graphics[ExtColorModeSelect] = t;	vga->misc |= 0x0C;	ctlr->flag |= Finit;}static voidload(Vga* vga, Ctlr* ctlr){	vgaxo(Grx, GeneralLockReg, vga->graphics[GeneralLockReg]);	vgaxo(Grx, ExtColorModeSelect, vga->graphics[ExtColorModeSelect]);	vgaxo(Grx, PanelDispCntlReg2, vga->graphics[PanelDispCntlReg2] & 0x39);	sleep(200);	generic.load(vga, ctlr);	vgaxo(Grx, ExtCRTDispAddr, vga->graphics[ExtCRTDispAddr]);	vgaxo(Grx, ExtCRTOffset, vga->graphics[ExtCRTOffset] & 0x39);	vgaxo(Grx, SysIfaceCntl1, vga->graphics[SysIfaceCntl1]);	if(ctlr->flag & Ulinear)		vga->graphics[SysIfaceCntl2] |= 0x80;	vgaxo(Grx, SysIfaceCntl2, vga->graphics[SysIfaceCntl2]);	vgaxo(Grx, SingleAddrPage, vga->graphics[SingleAddrPage]);	vgaxo(Grx, DualAddrPage, vga->graphics[DualAddrPage]);	vgaxo(Grx, PanelDispCntlReg1, vga->graphics[PanelDispCntlReg1]);	vgaxo(Grx, PanelDispCntlReg2, vga->graphics[PanelDispCntlReg2]);	vgaxo(Grx, PanelDispCntlReg3, vga->graphics[PanelDispCntlReg3]);	vgaxo(Grx, PanelVertCenterReg1, vga->graphics[PanelVertCenterReg1]);	vgaxo(Grx, PanelVertCenterReg2, vga->graphics[PanelVertCenterReg2]);	vgaxo(Grx, PanelVertCenterReg3, vga->graphics[PanelVertCenterReg3]);	vgaxo(Grx, PanelVertCenterReg4, vga->graphics[PanelVertCenterReg4]);	vgaxo(Grx, PanelHorizCenterReg1, vga->graphics[PanelHorizCenterReg1]);	vgaxo(Grx, PanelHorizCenterReg2, vga->graphics[PanelHorizCenterReg2]);	vgaxo(Grx, PanelHorizCenterReg3, vga->graphics[PanelHorizCenterReg3]);	vgaxo(Grx, PanelHorizCenterReg4, vga->graphics[PanelHorizCenterReg4]);	vgaxo(Grx, PanelVertCenterReg5, vga->graphics[PanelVertCenterReg5]);	vgaxo(Grx, PanelHorizCenterReg5, vga->graphics[PanelHorizCenterReg5]);	if(vga->mode->z != 8)		palette.load(vga, ctlr);}static voiddump(Vga* vga, Ctlr* ctlr){	int i;	char buf[100];	generic.dump(vga, ctlr);	for(i = 0; crts[i] >= 0; i++){		sprint(buf, "Crt%2.2uX", crts[i]);		printitem(ctlr->name, buf);		printreg(vga->crt[crts[i]]);	}	printitem(ctlr->name, "Crt40");	for(i=0x40; i<=0x59; i++)		printreg(vga->crt[i]);	printitem(ctlr->name, "Crt60");	for(i=0x60; i<=0x69; i++)		printreg(vga->crt[i]);	printitem(ctlr->name, "Crt70");	for (i = 0x70; i <= MaxCRT; i++)		printreg(vga->crt[i]);	printitem(ctlr->name, "Gr08");	for(i=0x08; i<=0x3F; i++)		printreg(vga->graphics[i]);	printitem(ctlr->name, "Gr70");	for(i=0x70; i<=MaxGR; i++)		printreg(vga->graphics[i]);}Ctlr neomagic = {	"neomagic",			/* name */	snarf,				/* snarf */	options,			/* options */	init,				/* init */	load,				/* load */	dump,				/* dump */};Ctlr neomagichwgc = {	"neomagichwgc",			/* name */	0,				/* snarf */	0,				/* options */	0,				/* init */	0,				/* load */	0,				/* dump */};

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -