~kris/9p

9hist

7f5fa5ddf05052d2cd74240bb7e893495dd6cd5e — David du Colombier 29 years ago 66ed55a
Plan 9 from Bell Labs 1997-07-16
1 files changed, 204 insertions(+), 0 deletions(-)

M pc/vgaclgd542x.c
M pc/vgaclgd542x.c => pc/vgaclgd542x.c +204 -0
@@ 9,7 9,11 @@
#include "screen.h"
#include "vga.h"

extern Bitmap gscreen;
extern Cursor curcursor;

static Lock clgd542xlock;
static ulong storage;

static void
clgd542xpage(int page)


@@ 19,6 23,205 @@ clgd542xpage(int page)
	unlock(&clgd542xlock);
}

static void
disable(void)
{
	uchar sr12;

	lock(&clgd542xlock);
	sr12 = vgaxi(Seqx, 0x12);
	vgaxo(Seqx, 0x12, sr12 & ~0x01);
	unlock(&clgd542xlock);
}

static void
enable(void)
{
	uchar sr12;
 
	/*
	 * Disable the cursor.
	 */
	lock(&clgd542xlock);
	sr12 = vgaxi(Seqx, 0x12);
	vgaxo(Seqx, 0x12, sr12 & ~0x01);

	/*
	 * Cursor colours.  
	 */
	vgaxo(Seqx, 0x12, sr12|0x02);
	setcolor(0x00, Pwhite<<(32-6), Pwhite<<(32-6), Pwhite<<(32-6));
	setcolor(0x0F, Pblack<<(32-6), Pblack<<(32-6), Pblack<<(32-6));
	vgaxo(Seqx, 0x12, sr12);

	/*
	 * Memory size. The BIOS leaves this in Seq0A, bits 4 and 3.
	 * See Technical Reference Manual Appendix E1, Section 1.3.2.
	 *
	 * The storage area for the 64x64 cursors is the last 16Kb of
	 * display memory.
	 */
	switch((vgaxi(Seqx, 0x0A)>>3) & 0x03){

	case 0:
		storage = (256-16)*1024;
		break;

	case 1:
		storage = (512-16)*1024;
		break;

	case 2:
		storage = (1024-16)*1024;
		break;

	case 3:
		storage = (2048-16)*1024;
		break;
	}
 
	/*
	 * Set the current cursor to index 0
	 * and turn the 64x64 cursor on.
	 */
	vgaxo(Seqx, 0x13, 0);
	vgaxo(Seqx, 0x12, sr12|0x05);

	unlock(&clgd542xlock);
}

static void
initcursor(Cursor* c, int xo, int yo, int index)
{
	uchar *p;
	uint p0, p1;
	int x, y;

	/*
	 * Is linear addressing turned on? This will determine
	 * how we access the cursor storage.
	 */
	if(vgaxi(Seqx, 0x07) & 0xF0)
		p = ((uchar*)gscreen.base) + storage;
	else {
		vgaxo(Grx, 0x09, (storage>>16)<<4);
		p = ((uchar*)gscreen.base) + (storage & 0xFFFF);
	}
	p += index*1024;

	for(y = yo; y < 16; y++){
		p0 = c->clr[2*y];
		p1 = c->clr[2*y+1];
		if(xo){
			p0 = (p0<<xo)|(p1>>(8-xo));
			p1 <<= xo;
		}
		*p++ = p0;
		*p++ = p1;

		for(x = 16; x < 64; x += 8)
			*p++ = 0x00;

		p0 = c->clr[2*y]|c->set[2*y];
		p1 = c->clr[2*y+1]|c->set[2*y+1];
		if(xo){
			p0 = (p0<<xo)|(p1>>(8-xo));
			p1 <<= xo;
		}
		*p++ = p0;
		*p++ = p1;

		for(x = 16; x < 64; x += 8)
			*p++ = 0x00;
	}
	while(y < 64+yo){
		for(x = 0; x < 64; x += 8){
			*p++ = 0x00;
			*p++ = 0x00;
		}
		y++;
	}
}

static void
load(Cursor* c)
{
	uchar sr12;

	/*
	 * Lock the display memory so we can update the
	 * cursor bitmap if necessary.
	 * Disable the cursor.
	 * If it's the same as the last cursor loaded,
	 * just make sure it's enabled and index 0.
	 */
	lock(&clgd542xlock);
	sr12 = vgaxi(Seqx, 0x12);
	vgaxo(Seqx, 0x12, sr12 & ~0x01);

	if(memcmp(c, &curcursor, sizeof(Cursor)) == 0){
		vgaxo(Seqx, 0x13, 0);
		vgaxo(Seqx, 0x12, sr12|0x05);
		unlock(&clgd542xlock);
		return;
	}
	memmove(&curcursor, c, sizeof(Cursor));
	initcursor(c, 0, 0, 0);

	/*
	 * Enable the cursor.
	 */
	vgaxo(Seqx, 0x13, 0);
	vgaxo(Seqx, 0x12, sr12|0x05);

	unlock(&clgd542xlock);
}

static int
move(Point p)
{
	int index, x, xo, y, yo;

	if(canlock(&clgd542xlock) == 0)
		return 1;

	index = 0;
	if((x = p.x+curcursor.offset.x) < 0){
		xo = -x;
		x = 0;
	}
	else
		xo = 0;
	if((y = p.y+curcursor.offset.y) < 0){
		yo = -y;
		y = 0;
	}
	else
		yo = 0;

	if(xo || yo){
		initcursor(&curcursor, xo, yo, 1);
		index = 1;
	}
	vgaxo(Seqx, 0x13, index<<2);
	
	vgaxo(Seqx, 0x10|((x & 0x07)<<5), (x>>3) & 0xFF);
	vgaxo(Seqx, 0x11|((y & 0x07)<<5), (y>>3) & 0xFF);

	unlock(&clgd542xlock);
	return 0;
}

static Hwgc clgd542xhwgc = {
	"clgd542xhwgc",
	enable,
	load,
	move,
	disable,

	0,
};

static Vgac clgd542x = {
	"clgd542x",
	clgd542xpage,


@@ 30,4 233,5 @@ void
vgaclgd542xlink(void)
{
	addvgaclink(&clgd542x);
	addhwgclink(&clgd542xhwgc);
}