ref: 806353ec9eda162a3ff13cad1e5228c58cd67566
parent: 874e71c8dc489b820c9a6066d13c470a34d7f83f
author: cinap_lenrek <[email protected]>
date: Sun Dec 27 18:08:59 EST 2020
devvga: implement screen tilting, remove panning and overlays Tilting allows using left/right rotated or invetrted display orientation. This can be changed at runtime such as: echo tilt right > /dev/vgactl This removes the old panning and vga overlays as they are only implemented with some ancient vga controllers.
--- a/sys/man/3/vga
+++ b/sys/man/3/vga
@@ -6,8 +6,6 @@
.B bind #v /dev
.B /dev/vgactl
-.B /dev/vgaovl
-.B /dev/vgaovlctl
.fi
.SH DESCRIPTION
The VGA device allows configuration of a graphics controller
@@ -48,9 +46,8 @@
.I Y
pixels high.
This message is optional;
-it is used to implement panning and to accommodate
-displays that require the in-memory screen image
-to have certain alignment properties.
+it is used to accommodate displays that require the
+in-memory screen image to have certain alignment properties.
For example, a 1400x1050 screen with a 1408x1050 in-memory image
will use
.B "size 1408x1050
@@ -57,22 +54,17 @@
but
.BR "actualsize 1400x1050" .
.TP
-.BI panning " mode"
-Depending on whether
-.I mode
-is
-.B on
-or
-.BR off ,
-enable or disable panning in a virtual screen.
-If panning is on and the screen's
-.B size
-is larger than its
-.BR actualsize ,
-the displayed portion of the screen will pan to follow the mouse.
-Setting the panning mode after the first attach of the
-.B #i
-driver has no effect.
+.BI tilt " value"
+Set the tilt of the screen,
+altering the screen's orientation.
+The
+.I value
+can be one of:
+.BR none ,
+.BR left ,
+.B inverted
+and
+.BR right .
.TP
.BI type " ctlr"
Set the type of VGA controller being used.
@@ -206,46 +198,6 @@
Reading
.B vgactl
returns the current settings, one per line.
-.PP
-Some VGA cards support overlay graphics.
-Writing strings to
-.B vgaovlctl
-configures such cards.
-The following are valid overlay control commands:
-.TP
-.BI openctl
-opens the overlay device.
-.TP
-.BI configure " w h format"
-allocates resources inside the driver to support an overlay area
-of width
-.I w
-and height
-.I h
-pixels. Currently, the only supported
-.I format
-is
-.B YUYV
-packed.
-In
-.B YUYV
-two pixels are encoded by their separate Y values
-and their combined U and V values.
-The size of the two pixels is 32 bits.
-.TP
-.BI enable " x y w h"
-enables drawing data on the display through the overlay mode. The data
-is drawn at position
-.IR x , y
-and has a width and height of
-.IR w , h
-respectively.
-.TP
-.BI closectl
-terminates overlay control.
-.PP
-Overlay data can be written to
-.BR vgaovl .
.SH EXAMPLES
The following disables hardware acceleration.
.IP
--- a/sys/src/9/pc/devvga.c
+++ b/sys/src/9/pc/devvga.c
@@ -19,15 +19,11 @@
enum {
Qdir,
Qvgactl,
- Qvgaovl,
- Qvgaovlctl,
};
static Dirtab vgadir[] = {
- ".", { Qdir, 0, QTDIR }, 0, 0550,
- "vgactl", { Qvgactl, 0 }, 0, 0660,
- "vgaovl", { Qvgaovl, 0 }, 0, 0660,
- "vgaovlctl", { Qvgaovlctl, 0 }, 0, 0660,
+ ".", { Qdir, 0, QTDIR }, 0, 0550,
+ "vgactl", { Qvgactl, 0 }, 0, 0660,
};
enum {
@@ -38,12 +34,12 @@
CMhwgc,
CMlinear,
CMpalettedepth,
- CMpanning,
CMsize,
CMtextmode,
CMtype,
CMsoftscreen,
CMpcidev,
+ CMtilt,
};
static Cmdtab vgactlmsg[] = {
@@ -54,12 +50,12 @@
CMhwgc, "hwgc", 2,
CMlinear, "linear", 0,
CMpalettedepth, "palettedepth", 2,
- CMpanning, "panning", 2,
CMsize, "size", 3,
CMtextmode, "textmode", 1,
CMtype, "type", 2,
CMsoftscreen, "softscreen", 2,
CMpcidev, "pcidev", 2,
+ CMtilt, "tilt", 2,
};
static void
@@ -120,35 +116,12 @@
static Chan*
vgaopen(Chan* c, int omode)
{
- VGAscr *scr;
- static char *openctl = "openctl\n";
-
- scr = &vgascreen[0];
- if ((ulong)c->qid.path == Qvgaovlctl) {
- if (scr->dev && scr->dev->ovlctl)
- scr->dev->ovlctl(scr, c, openctl, strlen(openctl));
- else
- error(Enonexist);
- }
return devopen(c, omode, vgadir, nelem(vgadir), devgen);
}
static void
-vgaclose(Chan* c)
+vgaclose(Chan*)
{
- VGAscr *scr;
- static char *closectl = "closectl\n";
-
- scr = &vgascreen[0];
- if((ulong)c->qid.path == Qvgaovlctl)
- if(scr->dev && scr->dev->ovlctl){
- if(waserror()){
- print("ovlctl error: %s\n", up->errstr);
- return;
- }
- scr->dev->ovlctl(scr, c, closectl, strlen(closectl));
- poperror();
- }
}
static long
@@ -176,19 +149,20 @@
p = seprint(p, e, "type %s\n",
scr->dev != nil ? scr->dev->name : "cga");
if(scr->gscreen != nil) {
+ Rectangle r;
+
p = seprint(p, e, "size %dx%dx%d %s\n",
- scr->gscreen->r.max.x, scr->gscreen->r.max.y,
- scr->gscreen->depth, chantostr(chbuf, scr->gscreen->chan));
- if(Dx(scr->gscreen->r) != Dx(physgscreenr)
- || Dy(scr->gscreen->r) != Dy(physgscreenr))
- p = seprint(p, e, "actualsize %dx%d\n",
- physgscreenr.max.x, physgscreenr.max.y);
+ scr->width, scr->height, scr->gscreen->depth,
+ chantostr(chbuf, scr->gscreen->chan));
+ r = actualscreensize(scr);
+ if(scr->width != r.max.x || scr->height != r.max.y)
+ p = seprint(p, e, "actualsize %dx%d\n", r.max.x, r.max.y);
+ p = seprint(p, e, "tilt %s\n", tiltstr[scr->tilt]);
}
p = seprint(p, e, "hwgc %s\n",
scr->cur != nil ? scr->cur->name : "off");
p = seprint(p, e, "hwaccel %s\n", hwaccel ? "on" : "off");
p = seprint(p, e, "hwblank %s\n", hwblank ? "on" : "off");
- p = seprint(p, e, "panning %s\n", panning ? "on" : "off");
p = seprint(p, e, "addr p 0x%.8llux v %#p size %#ux\n",
scr->paddr, scr->vaddr, scr->apsize);
p = seprint(p, e, "softscreen %s\n", scr->softscreen ? "on" : "off");
@@ -199,11 +173,6 @@
return n;
- case Qvgaovl:
- case Qvgaovlctl:
- error(Ebadusefd);
- break;
-
default:
error(Egreg);
break;
@@ -216,18 +185,16 @@
static char Enoscreen[] = "set the screen size first";
static void
-vgactl(Cmdbuf *cb)
+vgactl(VGAscr *scr, Cmdbuf *cb)
{
- int align, i, size, x, y, z;
+ int align, size, tilt, z, i;
Rectangle r;
char *chanstr, *p;
ulong chan;
Cmdtab *ct;
- VGAscr *scr;
extern VGAdev *vgadev[];
extern VGAcur *vgacur[];
- scr = &vgascreen[0];
ct = lookupcmd(cb, vgactlmsg, nelem(vgactlmsg));
switch(ct->index){
case CMhwgc:
@@ -298,14 +265,15 @@
return;
case CMsize:
- x = strtoul(cb->f[1], &p, 0);
+ r.min = ZP;
+ r.max.x = strtoul(cb->f[1], &p, 0);
if(*p)
p++;
- y = strtoul(p, &p, 0);
+ r.max.y = strtoul(p, &p, 0);
if(*p)
p++;
z = strtoul(p, &p, 0);
- if(badrect(Rect(0,0,x,y)))
+ if(badrect(r))
error(Ebadarg);
chanstr = cb->f[2];
if((chan = strtochan(chanstr)) == 0)
@@ -313,32 +281,30 @@
if(chantodepth(chan) != z)
error("depth, channel do not match");
deletescreenimage();
- if(screensize(x, y, z, chan))
- error(Egreg);
- bootscreenconf(scr);
+ setscreensize(scr, r.max.x, r.max.y, z, chan, scr->tilt);
return;
case CMactualsize:
if(scr->gscreen == nil)
error(Enoscreen);
- x = strtoul(cb->f[1], &p, 0);
+ r.min = ZP;
+ r.max.x = strtoul(cb->f[1], &p, 0);
if(*p)
p++;
- y = strtoul(p, nil, 0);
- r = Rect(0,0,x,y);
+ r.max.y = strtoul(p, nil, 0);
if(badrect(r))
error(Ebadarg);
- if(!rectinrect(r, scr->gscreen->r))
+ if(r.max.x > scr->width || r.max.y > scr->height)
error("physical screen bigger than virtual");
deletescreenimage();
- physgscreenr = r;
+ setactualsize(scr, r);
goto Resized;
case CMpalettedepth:
- x = strtoul(cb->f[1], &p, 0);
- if(x != 8 && x != 6)
+ z = strtoul(cb->f[1], &p, 0);
+ if(z != 8 && z != 6)
error(Ebadarg);
- scr->palettedepth = x;
+ scr->palettedepth = z;
return;
case CMsoftscreen:
@@ -348,17 +314,22 @@
scr->softscreen = 0;
else
break;
+ if(0){
+ case CMtilt:
+ for(tilt = 0; tilt < nelem(tiltstr); tilt++)
+ if(strcmp(cb->f[1], tiltstr[tilt]) == 0)
+ break;
+ } else {
+ tilt = scr->tilt;
+ }
if(scr->gscreen == nil)
return;
- r = physgscreenr;
- x = scr->gscreen->r.max.x;
- y = scr->gscreen->r.max.y;
- z = scr->gscreen->depth;
+ r = actualscreensize(scr);
chan = scr->gscreen->chan;
+ z = scr->gscreen->depth;
deletescreenimage();
- if(screensize(x, y, z, chan))
- error(Egreg);
- physgscreenr = r;
+ setscreensize(scr, scr->width, scr->height, z, chan, tilt);
+ setactualsize(scr, r);
/* no break */
case CMdrawinit:
if(scr->gscreen == nil)
@@ -368,7 +339,6 @@
hwblank = scr->blank != nil;
hwaccel = scr->fill != nil || scr->scroll != nil;
Resized:
- scr->gscreen->clipr = panning ? scr->gscreen->r : physgscreenr;
vgascreenwin(scr);
resetscreenimage();
return;
@@ -381,27 +351,10 @@
align = 0;
else
align = strtoul(cb->f[2], 0, 0);
- if(screenaperture(size, align) < 0)
+ if(screenaperture(scr, size, align) < 0)
error("not enough free address space");
return;
- case CMpanning:
- if(strcmp(cb->f[1], "on") == 0){
- if(scr->cur == nil)
- error("set cursor first");
- if(!scr->cur->doespanning)
- error("panning not supported");
- panning = 1;
- }
- else if(strcmp(cb->f[1], "off") == 0){
- panning = 0;
- }else
- break;
- if(scr->gscreen == nil)
- return;
- deletescreenimage();
- goto Resized;
-
case CMhwaccel:
if(strcmp(cb->f[1], "on") == 0)
hwaccel = 1;
@@ -424,14 +377,11 @@
cmderror(cb, "bad VGA control message");
}
-char Enooverlay[] = "No overlay support";
-
static long
vgawrite(Chan* c, void* a, long n, vlong off)
{
ulong offset = off;
Cmdbuf *cb;
- VGAscr *scr;
switch((ulong)c->qid.path){
@@ -446,26 +396,9 @@
free(cb);
nexterror();
}
- vgactl(cb);
+ vgactl(&vgascreen[0], cb);
poperror();
free(cb);
- return n;
-
- case Qvgaovl:
- scr = &vgascreen[0];
- if (scr->dev == nil || scr->dev->ovlwrite == nil) {
- error(Enooverlay);
- break;
- }
- return scr->dev->ovlwrite(scr, a, n, off);
-
- case Qvgaovlctl:
- scr = &vgascreen[0];
- if (scr->dev == nil || scr->dev->ovlctl == nil) {
- error(Enooverlay);
- break;
- }
- scr->dev->ovlctl(scr, c, a, n);
return n;
default:
--- a/sys/src/9/pc/screen.c
+++ b/sys/src/9/pc/screen.c
@@ -16,40 +16,78 @@
extern VGAcur vgasoftcur;
-Rectangle physgscreenr;
-
Memimage *gscreen;
VGAscr vgascreen[1];
-int
-screensize(int x, int y, int, ulong chan)
+char *tiltstr[4] = {
+ "none",
+ "left",
+ "inverted",
+ "right",
+};
+
+static Point
+tiltpt(int tilt, Point dim, Point p)
{
- VGAscr *scr;
+ switch(tilt&3){
+ case 1: return Pt(dim.y-p.y-1, p.x);
+ case 2: return Pt(dim.x-p.x-1, dim.y-p.y-1);
+ case 3: return Pt(p.y, dim.x-p.x-1);
+ }
+ return p;
+}
+static Rectangle
+tiltrect(int tilt, Point dim, Rectangle r)
+{
+ switch(tilt&3){
+ case 1: return Rect(dim.y-r.max.y, r.min.x, dim.y-r.min.y, r.max.x);
+ case 2: return Rect(dim.x-r.max.x, dim.y-r.max.y, dim.x-r.min.x, dim.y-r.min.y);
+ case 3: return Rect(r.min.y, dim.x-r.max.x, r.max.y, dim.x-r.min.x);
+ }
+ return r;
+}
+
+static Point
+tiltsize(int tilt, Point dim)
+{
+ return (tilt & 1) != 0 ? Pt(dim.y, dim.x) : dim;
+}
+
+Rectangle
+actualscreensize(VGAscr *scr)
+{
+ return Rpt(ZP, tiltsize(-scr->tilt, scr->gscreen->clipr.max));
+}
+
+void
+setactualsize(VGAscr *scr, Rectangle r)
+{
qlock(&drawlock);
- if(waserror()){
+
+ r.min = ZP;
+ r.max = tiltsize(scr->tilt, r.max);
+ if(rectclip(&r, scr->gscreen->r) == 0){
qunlock(&drawlock);
- nexterror();
+ return;
}
+ scr->gscreen->clipr = r;
- if(memimageinit() < 0)
- error("memimageinit failed");
+ qunlock(&drawlock);
+}
- lock(&vgascreenlock);
- if(waserror()){
- unlock(&vgascreenlock);
- nexterror();
- }
+static char*
+setscreensize0(VGAscr *scr, int width, int height, int depth, ulong chan, int tilt)
+{
+ int bpp, pitch;
- scr = &vgascreen[0];
scr->gscreendata = nil;
scr->gscreen = nil;
- if(gscreen){
+ if(gscreen != nil){
freememimage(gscreen);
gscreen = nil;
}
-
if(scr->paddr == 0){
if(scr->dev && scr->dev->page){
scr->vaddr = KADDR(VGAMEM());
@@ -57,8 +95,15 @@
}
scr->softscreen = 1;
}
+
+ depth = chantodepth(chan);
+ bpp = (depth+7) / 8;
+ pitch = ((width * depth+31) & ~31) / 8;
+
+ if(tilt)
+ scr->softscreen = 1;
if(scr->softscreen){
- gscreen = allocmemimage(Rect(0,0,x,y), chan);
+ gscreen = allocmemimage(Rpt(ZP, tiltsize(tilt, Pt(width, height))), chan);
scr->useflush = 1;
}else{
static Memdata md;
@@ -66,20 +111,52 @@
md.ref = 1;
if((md.bdata = scr->vaddr) == 0)
error("framebuffer not maped");
- gscreen = allocmemimaged(Rect(0,0,x,y), chan, &md);
+ gscreen = allocmemimaged(Rpt(ZP, Pt(width, height)), chan, &md);
scr->useflush = scr->dev && scr->dev->flush;
}
if(gscreen == nil)
- error("no memory for vga memimage");
+ return "no memory for vga memimage";
+ scr->bpp = bpp;
+ scr->pitch = pitch;
+ scr->width = width;
+ scr->height = height;
+ scr->tilt = tilt & 3;
+
scr->palettedepth = 6; /* default */
scr->memdefont = getmemdefont();
scr->gscreen = gscreen;
scr->gscreendata = gscreen->data;
- physgscreenr = gscreen->r;
+ return nil;
+}
+void
+setscreensize(VGAscr *scr, int x, int y, int z, ulong chan, int tilt)
+{
+ char *err;
+
+ qlock(&drawlock);
+ if(waserror()){
+ qunlock(&drawlock);
+ nexterror();
+ }
+
+ if(memimageinit() < 0)
+ error("memimageinit failed");
+
+ lock(&vgascreenlock);
+ if(waserror()){
+ unlock(&vgascreenlock);
+ nexterror();
+ }
+
+ err = setscreensize0(scr, x, y, z, chan, tilt);
+ if(err != nil)
+ error(err);
+
vgaimageinit(chan);
+ bootscreenconf(scr);
unlock(&vgascreenlock);
poperror();
@@ -86,26 +163,27 @@
drawcmap();
+ if(scr->cur && scr->cur != &vgasoftcur){
+ cursoroff();
+ setcursor(&cursor);
+ cursoron();
+ }
+
qunlock(&drawlock);
poperror();
-
- return 0;
}
int
-screenaperture(int size, int align)
+screenaperture(VGAscr *scr, int size, int align)
{
- VGAscr *scr;
uvlong pa;
- scr = &vgascreen[0];
+ if(size == 0)
+ return 0;
if(scr->paddr) /* set up during enable */
return 0;
- if(size == 0)
- return 0;
-
if(scr->dev && scr->dev->linear){
scr->dev->linear(scr, size, align);
return 0;
@@ -152,19 +230,61 @@
{
VGAscr *scr;
uchar *sp, *disp, *sdisp, *edisp;
- int y, len, incs, off, page;
+ int x, y, len, incs, off, page;
scr = &vgascreen[0];
if(scr->gscreen == nil || scr->useflush == 0)
return;
- if(rectclip(&r, scr->gscreen->r) == 0)
+ if(rectclip(&r, scr->gscreen->clipr) == 0)
return;
+
+ if(scr->tilt){
+ Point size;
+
+ /* only supported on linear framebuffer */
+ disp = scr->vaddr;
+ if(scr->paddr == 0 || disp == nil)
+ return;
+
+ size = scr->gscreen->clipr.max;
+ r = tiltrect(-scr->tilt, size, r);
+ size = tiltsize(-scr->tilt, size);
+ sp = byteaddr(scr->gscreen, tiltpt(scr->tilt, size, r.min));
+ incs = byteaddr(scr->gscreen, tiltpt(scr->tilt, size, Pt(r.min.x+1, r.min.y))) - sp;
+
+ for(;;){
+ sdisp = disp + r.min.y * scr->pitch;
+ for(x = r.min.x; x < r.max.x; x++, sp += incs){
+ switch(scr->bpp){
+ case 4:
+ ((ulong*)sdisp)[x] = *(ulong*)sp;
+ break;
+ case 3:
+ sdisp[x*3+0] = sp[0];
+ sdisp[x*3+1] = sp[1];
+ sdisp[x*3+2] = sp[2];
+ break;
+ case 2:
+ ((ushort*)sdisp)[x] = *(ushort*)sp;
+ break;
+ case 1:
+ sdisp[x] = sp[0];
+ break;
+ }
+ }
+ if(++r.min.y >= r.max.y)
+ break;
+ sp = byteaddr(scr->gscreen, tiltpt(scr->tilt, size, r.min));
+ }
+ return;
+ }
+
if(scr->dev && scr->dev->flush){
scr->dev->flush(scr, r);
return;
}
disp = scr->vaddr;
- incs = scr->gscreen->width*sizeof(ulong);
+ incs = scr->pitch;
off = (r.min.x*scr->gscreen->depth) / 8;
len = (r.max.x*scr->gscreen->depth + 7) / 8;
len -= off;
@@ -299,16 +419,48 @@
return setpalette(p, r, g, b);
}
+static void
+tiltcursor(int t, Cursor *src, Cursor *dst)
+{
+ static Point dim = {16, 16};
+ uint i, j, im, jm;
+ Point p;
+
+ for(i = 0; i < 16*16; i++){
+ p = tiltpt(t, dim, Pt(i&15,i>>4));
+ j = p.y<<4 | p.x;
+ im = 0x80>>(i&7);
+ jm = 0x80>>(j&7);
+ if(src->clr[i>>3] & im)
+ dst->clr[j>>3] |= jm;
+ else
+ dst->clr[j>>3] &= ~jm;
+ if(src->set[i>>3] & im)
+ dst->set[j>>3] |= jm;
+ else
+ dst->set[j>>3] &= ~jm;
+ }
+
+ p = Pt(-src->offset.x & 15, -src->offset.y & 15);
+ p = tiltpt(t, dim, p);
+ dst->offset = Pt(-p.x, -p.y);
+}
+
void
cursoron(void)
{
VGAscr *scr;
VGAcur *cur;
+ Point p;
scr = &vgascreen[0];
cur = scr->cur;
- if(cur && cur->move)
- cur->move(scr, mousexy());
+ if(cur && cur->move){
+ p = mousexy();
+ if(scr->tilt && cur != &vgasoftcur)
+ p = tiltpt(-scr->tilt, scr->gscreen->clipr.max, p);
+ cur->move(scr, p);
+ }
}
void
@@ -324,13 +476,18 @@
scr = &vgascreen[0];
cur = scr->cur;
- if(cur && cur->load)
+ if(cur && cur->load){
+ if(scr->tilt && cur != &vgasoftcur){
+ static Cursor tmp;
+ tiltcursor(-scr->tilt, curs, &tmp);
+ curs = &tmp;
+ }
cur->load(scr, curs);
+ }
}
int hwaccel = 0;
int hwblank = 0;
-int panning = 0;
int
hwdraw(Memdrawparam *par)
@@ -358,7 +515,7 @@
if(mask && mask->data->bdata == scrd->bdata)
swcursoravoid(par->mr);
}
- if(!hwaccel || scr->softscreen)
+ if(!hwaccel || scr->softscreen || scr->tilt)
return 0;
if(dst->data->bdata != scrd->bdata || src == nil || mask == nil)
return 0;
@@ -396,13 +553,13 @@
{
VGAscr *scr;
+ if(!hwblank)
+ return;
scr = &vgascreen[0];
- if(hwblank){
- if(scr->blank)
- scr->blank(scr, blank);
- else
- vgablank(scr, blank);
- }
+ if(scr->blank)
+ scr->blank(scr, blank);
+ else
+ vgablank(scr, blank);
}
static char*
@@ -461,6 +618,8 @@
Pcidev *p;
p = scr->pci;
+ if(p == nil)
+ return "no pci card";
/*
* Scan for largest memory region on card.
@@ -575,7 +734,7 @@
bootscreeninit(void)
{
VGAscr *scr;
- int x, y, z;
+ int x, y, z, tilt;
uvlong pa;
ulong chan, sz;
char *s, *p, *err;
@@ -608,35 +767,37 @@
pa = strtoull(p+1, &s, 0);
if(pa == 0)
return;
- if(*s++ == ' ')
- sz = strtoul(s, nil, 0);
+ if(*s == ' ')
+ sz = strtoul(s+1, nil, 0);
if(sz < x * y * (z+7)/8)
sz = x * y * (z+7)/8;
- /* map framebuffer */
+ tilt = 0;
+ if((p = getconf("tiltscreen")) != nil){
+ for(; tilt < nelem(tiltstr); tilt++)
+ if(strcmp(p, tiltstr[tilt]) == 0)
+ break;
+ tilt &= 3;
+ }
+
scr = &vgascreen[0];
+ scr->dev = nil;
+ scr->softscreen = 1;
+
if((err = bootmapfb(scr, pa, sz)) != nil){
print("bootmapfb: %s\n", err);
return;
}
- if(memimageinit() < 0)
+ if(memimageinit() < 0){
+ print("memimageinit failed\n");
return;
-
- gscreen = allocmemimage(Rect(0,0,x,y), chan);
- if(gscreen == nil)
+ }
+ if((err = setscreensize0(scr, x, y, z, chan, tilt)) != nil){
+ print("setscreensize0: %s\n", err);
return;
+ }
- scr->palettedepth = 6; /* default */
- scr->memdefont = getmemdefont();
- scr->gscreen = gscreen;
- scr->gscreendata = gscreen->data;
- scr->softscreen = 1;
- scr->useflush = 1;
- scr->dev = nil;
-
- physgscreenr = gscreen->r;
-
vgaimageinit(chan);
vgascreenwin(scr);
@@ -659,10 +820,11 @@
char conf[100], chan[30];
conf[0] = '\0';
- if(scr != nil && scr->paddr != 0 && scr->gscreen != nil)
+ if(scr != nil && scr->paddr != 0 && scr->gscreen != nil){
snprint(conf, sizeof(conf), "%dx%dx%d %s 0x%.8llux %d\n",
- scr->gscreen->r.max.x, scr->gscreen->r.max.y,
- scr->gscreen->depth, chantostr(chan, scr->gscreen->chan),
+ scr->width, scr->height, scr->gscreen->depth, chantostr(chan, scr->gscreen->chan),
scr->paddr, scr->apsize);
+ ksetenv("tiltscreen", tiltstr[scr->tilt], 1);
+ }
ksetenv("*bootscreen", conf, 1);
}
--- a/sys/src/9/pc/screen.h
+++ b/sys/src/9/pc/screen.h
@@ -75,8 +75,6 @@
void (*disable)(VGAscr*);
void (*load)(VGAscr*, Cursor*);
int (*move)(VGAscr*, Point);
-
- int doespanning;
};
/*
@@ -96,6 +94,12 @@
void* vaddr;
int apsize;
+ int bpp;
+ int pitch;
+
+ int width;
+ int height;
+
ulong io; /* device specific registers */
ulong *mmio;
@@ -110,8 +114,8 @@
int (*scroll)(VGAscr*, Rectangle, Rectangle);
void (*blank)(VGAscr*, int);
ulong id; /* internal identifier for driver use */
- int overlayinit;
int softscreen;
+ int tilt;
};
extern VGAscr vgascreen[];
@@ -128,7 +132,10 @@
/* screen.c */
extern int hwaccel; /* use hw acceleration */
extern int hwblank; /* use hw blanking */
-extern int panning; /* use virtual screen panning */
+extern char *tiltstr[4];
+extern Rectangle actualscreensize(VGAscr*);
+extern void setactualsize(VGAscr*, Rectangle);
+extern void setscreensize(VGAscr*, int, int, int, ulong, int);
extern void addvgaseg(char*, uvlong, ulong);
extern Memdata* attachscreen(Rectangle*, ulong*, int*, int*, int*);
extern void flushmemscreen(Rectangle);
@@ -135,9 +142,7 @@
extern void cursoron(void);
extern void cursoroff(void);
extern void setcursor(Cursor*);
-extern int screensize(int, int, int, ulong);
-extern int screenaperture(int, int);
-extern Rectangle physgscreenr; /* actual monitor size */
+extern int screenaperture(VGAscr*, int, int);
extern void blankscreen(int);
extern char* rgbmask2chan(char *buf, int depth, u32int rm, u32int gm, u32int bm);
extern void bootscreeninit(void);
--- a/sys/src/9/pc/vgact65545.c
+++ b/sys/src/9/pc/vgact65545.c
@@ -34,7 +34,7 @@
* Find a place for the cursor data in display memory.
* Must be on a 1024-byte boundary.
*/
- storage = ROUND(scr->gscreen->width*sizeof(ulong)*scr->gscreen->r.max.y, 1024);
+ storage = ROUND(scr->pitch*scr->height, 1024);
outl(0xB3D0, storage);
scr->storage = storage;
--- a/sys/src/9/pc/vgacyber938x.c
+++ b/sys/src/9/pc/vgacyber938x.c
@@ -170,7 +170,7 @@
/*
* Find a place for the cursor data in display memory.
*/
- storage = ((scr->gscreen->width*sizeof(ulong)*scr->gscreen->r.max.y+1023)/1024);
+ storage = ((scr->pitch*scr->height+1023)/1024);
vgaxo(Crtx, 0x44, storage & 0xFF);
vgaxo(Crtx, 0x45, (storage>>8) & 0xFF);
storage *= 1024;
--- a/sys/src/9/pc/vgaet4000.c
+++ b/sys/src/9/pc/vgaet4000.c
@@ -79,7 +79,7 @@
* 1024-byte boundary so that there's no danger of it
* crossing a page.
*/
- scr->storage = (scr->gscreen->width*sizeof(ulong)*scr->gscreen->r.max.y+1023)/1024;
+ scr->storage = (scr->pitch*scr->height+1023)/1024;
scr->storage *= 1024/4;
outb(0x217A, 0xE8);
outb(0x217B, scr->storage & 0xFF);
--- a/sys/src/9/pc/vgamach64xx.c
+++ b/sys/src/9/pc/vgamach64xx.c
@@ -80,12 +80,6 @@
#define HOST_MEM_MODE_V 0xC0000000
#define HOST_MEM_MODE_NORMAL HOST_YUV_APERTURE_UPPER
-static Chan *ovl_chan; /* Channel of controlling process */
-static int ovl_width; /* Width of input overlay buffer */
-static int ovl_height; /* Height of input overlay buffer */
-static int ovl_format; /* Overlay format */
-static ulong ovl_fib; /* Frame in bytes */
-
enum {
VTGTB1S1 = 0x01, /* Asic description for VTB1S1 and GTB1S1. */
VT4GTIIC = 0x3A, /* asic descr for VT4 and RAGE IIC */
@@ -117,7 +111,6 @@
static ulong mach64refclock;
static Mach64types *mach64type;
static int mach64revb; /* Revision B or greater? */
-static ulong mach64overlay; /* Overlay buffer */
static Mach64types mach64s[] = {
('C'<<8)|'T', 0, 1350000, /*?*/ 0, /* 4354: CT */
@@ -480,71 +473,12 @@
p.y>=r.min.y && p.y<=r.max.y;
}
-/*
- * If necessary, translate the rectangle physr
- * some multiple of [dx dy] so that it includes p.
- * Return 1 if the rectangle changed.
- */
static int
-screenpan(Point p, Rectangle *physr, int dx, int dy)
-{
- int d;
-
- if(ptalmostinrect(p, *physr))
- return 0;
-
- if(p.y < physr->min.y){
- d = physr->min.y - (p.y&~(dy-1));
- physr->min.y -= d;
- physr->max.y -= d;
- }
- if(p.y > physr->max.y){
- d = ((p.y+dy-1)&~(dy-1)) - physr->max.y;
- physr->min.y += d;
- physr->max.y += d;
- }
-
- if(p.x < physr->min.x){
- d = physr->min.x - (p.x&~(dx-1));
- physr->min.x -= d;
- physr->max.x -= d;
- }
- if(p.x > physr->max.x){
- d = ((p.x+dx-1)&~(dx-1)) - physr->max.x;
- physr->min.x += d;
- physr->max.x += d;
- }
- return 1;
-}
-
-static int
mach64xxcurmove(VGAscr* scr, Point p)
{
int x, xo, y, yo;
- int dx;
- ulong off, pitch;
/*
- * If the point we want to display is outside the current
- * screen rectangle, pan the screen to display it.
- *
- * We have to move in 64-bit chunks.
- */
- if(scr->gscreen->depth == 24)
- dx = (64*3)/24;
- else
- dx = 64 / scr->gscreen->depth;
-
- if(panning && screenpan(p, &physgscreenr, dx, 1)){
- off = (physgscreenr.min.y*Dx(scr->gscreen->r)+physgscreenr.min.x)/dx;
- pitch = Dx(scr->gscreen->r)/8;
- iow32(scr, CrtcOffPitch, (pitch<<22)|off);
- }
-
- p.x -= physgscreenr.min.x;
- p.y -= physgscreenr.min.y;
-
- /*
* Mustn't position the cursor offscreen even partially,
* or it disappears. Therefore, if x or y is -ve, adjust the
* cursor presets instead. If y is negative also have to
@@ -589,7 +523,7 @@
* Find a place for the cursor data in display memory.
* Must be 64-bit aligned.
*/
- storage = (scr->gscreen->width*sizeof(ulong)*scr->gscreen->r.max.y+7)/8;
+ storage = (scr->pitch*scr->height+7)/8;
iow32(scr, CurOffset, storage);
scr->storage = storage*8;
@@ -644,56 +578,15 @@
}
static void
-init_overlayclock(VGAscr *scr)
-{
- uchar *cc, save, pll_ref_div, pll_vclk_cntl, vclk_post_div,
- vclk_fb_div, ecp_div;
- int i;
- ulong dotclock;
-
- /* Taken from GLX */
- /* Get monitor dotclock, check for Overlay Scaler clock limit */
- cc = (uchar *)&scr->mmio[mmoffset[ClockCntl]];
- save = cc[1]; i = cc[0] & 3;
- cc[1] = 2<<2; pll_ref_div = cc[2];
- cc[1] = 5<<2; pll_vclk_cntl = cc[2];
- cc[1] = 6<<2; vclk_post_div = (cc[2]>>(i+i)) & 3;
- cc[1] = (7+i)<<2; vclk_fb_div = cc[2];
-
- dotclock = 2 * mach64refclock * vclk_fb_div /
- (pll_ref_div * (1 << vclk_post_div));
- /* ecp_div: 0=dotclock, 1=dotclock/2, 2=dotclock/4 */
- ecp_div = dotclock / mach64type->m64_ovlclock;
- if (ecp_div>2) ecp_div = 2;
-
- /* Force a scaler clock factor of 1 if refclock *
- * is unknown (VCLK_SRC not PLLVCLK) */
- if ((pll_vclk_cntl & 0x03) != 0x03)
- ecp_div = 0;
- if ((pll_vclk_cntl & 0x30) != ecp_div<<4) {
- cc[1] = (5<<2)|2;
- cc[2] = (pll_vclk_cntl&0xCF) | (ecp_div<<4);
- }
-
- /* Restore PLL Register Index */
- cc[1] = save;
-}
-
-static void
initengine(VGAscr *scr)
{
- ulong pitch;
uchar *bios;
ushort table;
- pitch = Dx(scr->gscreen->r)/8;
- if(scr->gscreen->depth == 24)
- pitch *= 3;
-
resetengine(scr);
waitforfifo(scr, 14);
iow32(scr, ContextMask, ~0);
- iow32(scr, DstOffPitch, pitch<<22);
+ iow32(scr, DstOffPitch, scr->pitch<<22);
iow32(scr, DstYX, 0);
iow32(scr, DstHeight, 0);
iow32(scr, DstBresErr, 0);
@@ -700,7 +593,7 @@
iow32(scr, DstBresInc, 0);
iow32(scr, DstBresDec, 0);
iow32(scr, DstCntl, 0x23);
- iow32(scr, SrcOffPitch, pitch<<22);
+ iow32(scr, SrcOffPitch, scr->pitch<<22);
iow32(scr, SrcYX, 0);
iow32(scr, SrcHeight1Width1, 1);
iow32(scr, SrcYXstart, 0);
@@ -793,7 +686,6 @@
static int
mach64hwfill(VGAscr *scr, Rectangle r, ulong sval)
{
- ulong pitch;
ulong ctl;
/* shouldn't happen */
@@ -800,12 +692,10 @@
if(scr->io == 0x2EC || scr->io == 0x1C8 || scr->io == 0)
return 0;
- pitch = Dx(scr->gscreen->r)/8;
ctl = 1|2; /* left-to-right, top-to-bottom */
if(scr->gscreen->depth == 24){
r.min.x *= 3;
r.max.x *= 3;
- pitch *= 3;
ctl |= (1<<7)|(((r.min.x/4)%6)<<8);
}
@@ -817,7 +707,7 @@
iow32(scr, ClrCmpCntl, 0x00000000);
iow32(scr, ScLeftRight, 0x1FFF0000);
iow32(scr, ScTopBottom, 0x1FFF0000);
- iow32(scr, DstOffPitch, pitch<<22);
+ iow32(scr, DstOffPitch, scr->pitch<<22);
iow32(scr, DstCntl, ctl);
iow32(scr, DstYX, (r.min.x<<16)|r.min.y);
iow32(scr, DstHeightWidth, (Dx(r)<<16)|Dy(r));
@@ -829,7 +719,6 @@
static int
mach64hwscroll(VGAscr *scr, Rectangle r, Rectangle sr)
{
- ulong pitch;
Point dp, sp;
ulong ctl;
int dx, dy;
@@ -836,10 +725,8 @@
dx = Dx(r);
dy = Dy(r);
- pitch = Dx(scr->gscreen->r)/8;
if(scr->gscreen->depth == 24){
dx *= 3;
- pitch *= 3;
r.min.x *= 3;
sr.min.x *= 3;
}
@@ -875,11 +762,11 @@
iow32(scr, ClrCmpCntl, 0x00000000);
waitforfifo(scr, 8);
- iow32(scr, SrcOffPitch, pitch<<22);
+ iow32(scr, SrcOffPitch, scr->pitch<<22);
iow32(scr, SrcCntl, 0x00000000);
iow32(scr, SrcYX, (sp.x<<16)|sp.y);
iow32(scr, SrcWidth1, dx);
- iow32(scr, DstOffPitch, pitch<<22);
+ iow32(scr, DstOffPitch, scr->pitch<<22);
iow32(scr, DstCntl, ctl);
iow32(scr, DstYX, (dp.x<<16)|dp.y);
@@ -957,222 +844,6 @@
}
}
-static void
-ovl_configure(VGAscr *scr, Chan *c, char **field)
-{
- int w, h;
- char *format;
-
- w = (int)strtol(field[1], nil, 0);
- h = (int)strtol(field[2], nil, 0);
- format = field[3];
-
- if (c != ovl_chan)
- error(Einuse);
- if (strcmp(format, "YUYV"))
- error(Eunsupportedformat);
-
- ovl_width = w;
- ovl_height = h;
- ovl_fib = w * h * sizeof(ushort);
-
- waitforidle(scr);
- scr->mmio[mmoffset[BusCntl]] |= 0x08000000; /* Enable regblock 1 */
- scr->mmio[mmoffset[OverlayScaleCntl]] =
- SCALE_ZERO_EXTEND|SCALE_RED_TEMP_6500K|
- SCALE_HORZ_BLEND|SCALE_VERT_BLEND;
- scr->mmio[mmoffset[!mach64revb? Buf0Pitch: ScalerBuf0Pitch]] = w;
- scr->mmio[mmoffset[CaptureConfig]] =
- SCALER_FRAME_READ_MODE_FULL|
- SCALER_BUF_MODE_SINGLE|
- SCALER_BUF_NEXT_0;
- scr->mmio[mmoffset[OverlayKeyCntl]] = !mach64revb?
- OVERLAY_MIX_ALWAYS_V|(OVERLAY_EXCLUSIVE_NORMAL << 28):
- 0x011;
-
- if (mach64type->m64_pro) {
- waitforfifo(scr, 6);
-
- /* set the scaler co-efficient registers */
- scr->mmio[mmoffset[ScalerColourCntl]] =
- (0x00) | (0x10 << 8) | (0x10 << 16);
- scr->mmio[mmoffset[ScalerHCoef0]] =
- (0x00) | (0x20 << 8);
- scr->mmio[mmoffset[ScalerHCoef1]] =
- (0x0D) | (0x20 << 8) | (0x06 << 16) | (0x0D << 24);
- scr->mmio[mmoffset[ScalerHCoef2]] =
- (0x0D) | (0x1C << 8) | (0x0A << 16) | (0x0D << 24);
- scr->mmio[mmoffset[ScalerHCoef3]] =
- (0x0C) | (0x1A << 8) | (0x0E << 16) | (0x0C << 24);
- scr->mmio[mmoffset[ScalerHCoef4]] =
- (0x0C) | (0x14 << 8) | (0x14 << 16) | (0x0C << 24);
- }
-
- waitforfifo(scr, 3);
- scr->mmio[mmoffset[VideoFormat]] = SCALE_IN_YVYU422 |
- (!mach64revb? 0xC: 0);
-
- if (mach64overlay == 0)
- mach64overlay = scr->storage + 64 * 64 * sizeof(uchar);
- scr->mmio[mmoffset[!mach64revb? Buf0Offset: ScalerBuf0Offset]] =
- mach64overlay;
-}
-
-static void
-ovl_enable(VGAscr *scr, Chan *c, char **field)
-{
- int x, y, w, h;
- long h_inc, v_inc;
-
- x = (int)strtol(field[1], nil, 0);
- y = (int)strtol(field[2], nil, 0);
- w = (int)strtol(field[3], nil, 0);
- h = (int)strtol(field[4], nil, 0);
-
- if (x < 0 || x + w > physgscreenr.max.x ||
- y < 0 || y + h > physgscreenr.max.y)
- error(Ebadarg);
-
- if (c != ovl_chan)
- error(Einuse);
- if (scr->mmio[mmoffset[CrtcGenCntl]] & 1) { /* double scan enable */
- y *= 2;
- h *= 2;
- }
-
- waitforfifo(scr, 2);
- scr->mmio[mmoffset[OverlayYX]] =
- ((x & 0xFFFF) << 16) | (y & 0xFFFF);
- scr->mmio[mmoffset[OverlayYXEnd]] =
- (((x + w) & 0xFFFF) << 16) | ((y + h) & 0xFFFF);
-
- h_inc = (ovl_width << 12) / (w >> 1); /* ??? */
- v_inc = (ovl_height << 12) / h;
- waitforfifo(scr, 2);
- scr->mmio[mmoffset[OverlayScaleInc]] =
- ((h_inc & 0xFFFF) << 16) | (v_inc & 0xFFFF);
- scr->mmio[mmoffset[ScalerHeightWidth]] =
- ((ovl_width & 0xFFFF) << 16) | (ovl_height & 0xFFFF);
- waitforidle(scr);
- scr->mmio[mmoffset[OverlayScaleCntl]] |=
- (SCALE_ENABLE|OVERLAY_ENABLE);
-}
-
-static void
-ovl_status(VGAscr *scr, Chan *, char **field)
-{
- pprint("%s: %s %.4uX, VT/GT %s, PRO %s, ovlclock %lud, rev B %s, refclock %ld\n",
- scr->dev->name, field[0], mach64type->m64_id,
- mach64type->m64_vtgt? "yes": "no",
- mach64type->m64_pro? "yes": "no",
- mach64type->m64_ovlclock,
- mach64revb? "yes": "no",
- mach64refclock);
- pprint("%s: storage @%.8luX, aperture @%8.ullX, ovl buf @%.8ulX\n",
- scr->dev->name, scr->storage, scr->paddr,
- mach64overlay);
-}
-
-static void
-ovl_openctl(VGAscr *, Chan *c, char **)
-{
- if (ovl_chan)
- error(Einuse);
- ovl_chan = c;
-}
-
-static void
-ovl_closectl(VGAscr *scr, Chan *c, char **)
-{
- if (c != ovl_chan) return;
-
- waitforidle(scr);
- scr->mmio[mmoffset[OverlayScaleCntl]] &=
- ~(SCALE_ENABLE|OVERLAY_ENABLE);
- ovl_chan = nil;
- ovl_width = ovl_height = ovl_fib = 0;
-}
-
-enum
-{
- CMclosectl,
- CMconfigure,
- CMenable,
- CMopenctl,
- CMstatus,
-};
-
-static void (*ovl_cmds[])(VGAscr *, Chan *, char **) =
-{
- [CMclosectl] ovl_closectl,
- [CMconfigure] ovl_configure,
- [CMenable] ovl_enable,
- [CMopenctl] ovl_openctl,
- [CMstatus] ovl_status,
-};
-
-static Cmdtab mach64xxcmd[] =
-{
- CMclosectl, "closectl", 1,
- CMconfigure, "configure", 4,
- CMenable, "enable", 5,
- CMopenctl, "openctl", 1,
- CMstatus, "status", 1,
-};
-
-static void
-mach64xxovlctl(VGAscr *scr, Chan *c, void *a, int n)
-{
- Cmdbuf *cb;
- Cmdtab *ct;
-
- if(!mach64type->m64_vtgt)
- error(Enodev);
-
- if(!scr->overlayinit){
- scr->overlayinit = 1;
- init_overlayclock(scr);
- }
- cb = parsecmd(a, n);
- if(waserror()){
- free(cb);
- nexterror();
- }
-
- ct = lookupcmd(cb, mach64xxcmd, nelem(mach64xxcmd));
-
- ovl_cmds[ct->index](scr, c, cb->f);
-
- poperror();
- free(cb);
-}
-
-static int
-mach64xxovlwrite(VGAscr *scr, void *a, int len, vlong offs)
-{
- uchar *src;
- int _len;
-
- if (ovl_chan == nil) return len; /* Acts as a /dev/null */
-
- /* Calculate the destination address */
- _len = len;
- src = (uchar *)a;
- while (len > 0) {
- ulong _offs;
- int nb;
-
- _offs = (ulong)(offs % ovl_fib);
- nb = (_offs + len > ovl_fib)? ovl_fib - _offs: len;
- memmove((uchar *)scr->vaddr + mach64overlay + _offs,
- src, nb);
- offs += nb;
- src += nb;
- len -= nb;
- }
- return _len;
-}
-
VGAdev vgamach64xxdev = {
"mach64xx",
@@ -1180,10 +851,7 @@
0, /* disable */
0, /* page */
mach64xxlinear, /* linear */
- mach64xxdrawinit, /* drawinit */
- 0,
- mach64xxovlctl, /* overlay control */
- mach64xxovlwrite, /* write the overlay */
+ mach64xxdrawinit, /* drawinit */
};
VGAcur vgamach64xxcur = {
@@ -1193,7 +861,5 @@
mach64xxcurdisable, /* disable */
mach64xxcurload, /* load */
mach64xxcurmove, /* move */
-
- 1 /* doespanning */
};
--- a/sys/src/9/pc/vgamga4xx.c
+++ b/sys/src/9/pc/vgamga4xx.c
@@ -405,7 +405,6 @@
mga4xxscroll(VGAscr *scr, Rectangle dr, Rectangle sr)
{
uchar * mga;
- int pitch;
int width, height;
ulong start, end, sgn;
Point sp, dp;
@@ -421,7 +420,6 @@
if(eqpt(sp, dp))
return 1;
- pitch = Dx(scr->gscreen->r);
width = Dx(sr);
height = Dy(sr);
sgn = 0;
@@ -433,7 +431,7 @@
}
width--;
- start = end = sp.x + (sp.y * pitch);
+ start = end = sp.x + (sp.y * scr->width);
if(dp.x > sp.x && dp.x < sp.x + width){
start += width;
@@ -445,7 +443,7 @@
mga_fifo(mga, 8);
mgawrite32(mga, DWGCTL, 0);
mgawrite32(mga, SGN, sgn);
- mgawrite32(mga, AR5, sgn & SGN_UP ? -pitch : pitch);
+ mgawrite32(mga, AR5, sgn & SGN_UP ? -scr->width : scr->width);
mgawrite32(mga, AR0, end);
mgawrite32(mga, AR3, start);
mgawrite32(mga, FXBNDRY, ((dp.x + width) << 16) | dp.x);
--- a/sys/src/9/pc/vganeomagic.c
+++ b/sys/src/9/pc/vganeomagic.c
@@ -376,8 +376,8 @@
| NEO_BC3_SKIP_MAPPING
| GXcopy;
mmio[DstStartOff] = scr->paddr
- + r.min.y*scr->gscreen->width*sizeof(ulong)
- + r.min.x*scr->gscreen->depth/BI2BY;
+ + r.min.y*scr->pitch
+ + r.min.x*scr->bpp;
mmio[XYExt] = (Dy(r) << 16) | (Dx(r) & 0xffff);
waitforidle(scr);
return 1;
@@ -387,13 +387,9 @@
neomagichwscroll(VGAscr *scr, Rectangle r, Rectangle sr)
{
ulong *mmio;
- int pitch, pixel;
mmio = scr->mmio;
- pitch = scr->gscreen->width*sizeof(ulong);
- pixel = scr->gscreen->depth/BI2BY;
-
waitforfifo(scr, 4);
if (r.min.y < sr.min.y || (r.min.y == sr.min.y && r.min.x < sr.min.x)) {
/* start from upper-left */
@@ -402,9 +398,9 @@
| NEO_BC3_SKIP_MAPPING
| GXcopy;
mmio[SrcStartOff] = scr->paddr
- + sr.min.y*pitch + sr.min.x*pixel;
+ + sr.min.y*scr->pitch + sr.min.x*scr->bpp;
mmio[DstStartOff] = scr->paddr
- + r.min.y*pitch + r.min.x*pixel;
+ + r.min.y*scr->pitch + r.min.x*scr->bpp;
} else {
/* start from lower-right */
mmio[BltCntl] = neomagicbltflags
@@ -415,9 +411,9 @@
| NEO_BC3_SKIP_MAPPING
| GXcopy;
mmio[SrcStartOff] = scr->paddr
- + (sr.max.y-1)*pitch + (sr.max.x-1)*pixel;
+ + (sr.max.y-1)*scr->pitch + (sr.max.x-1)*scr->bpp;
mmio[DstStartOff] = scr->paddr
- + (r.max.y-1)*pitch + (r.max.x-1)*pixel;
+ + (r.max.y-1)*scr->pitch + (r.max.x-1)*scr->bpp;
}
mmio[XYExt] = (Dy(r) << 16) | (Dx(r) & 0xffff);
waitforidle(scr);
@@ -428,12 +424,10 @@
neomagicdrawinit(VGAscr *scr)
{
ulong *mmio;
- uint bltmode, pitch;
+ uint bltmode;
mmio = scr->mmio;
- pitch = scr->gscreen->width*sizeof(ulong);
-
neomagicbltflags = bltmode = 0;
switch(scr->gscreen->depth) {
@@ -450,7 +444,7 @@
return;
}
- switch(Dx(scr->gscreen->r)) {
+ switch(scr->width) {
case 320:
bltmode |= NEO_MODE1_X_320;
neomagicbltflags |= NEO_BC1_X_320;
@@ -486,7 +480,7 @@
waitforidle(scr);
mmio[BltStat] = bltmode << 16;
- mmio[Pitch] = (pitch << 16) | (pitch & 0xffff);
+ mmio[Pitch] = (scr->pitch << 16) | (scr->pitch & 0xffff);
scr->fill = neomagichwfill;
scr->scroll = neomagichwscroll;
--- a/sys/src/9/pc/vganvidia.c
+++ b/sys/src/9/pc/vganvidia.c
@@ -343,13 +343,11 @@
nvresetgraphics(VGAscr *scr)
{
ulong surfaceFormat, patternFormat, rectFormat, lineFormat;
- int pitch, i;
+ int i;
if(scr->paddr == 0)
return -1;
- pitch = scr->gscreen->width*sizeof(ulong);
-
/*
* DMA is at the end of the virtual window,
* but we might have cut it short when mapping it.
@@ -416,7 +414,7 @@
nvdmastart(scr, SURFACE_FORMAT, 4);
nvdmanext(surfaceFormat);
- nvdmanext(pitch | (pitch << 16));
+ nvdmanext(scr->pitch | (scr->pitch << 16));
nvdmanext(0);
nvdmanext(0);
--- a/sys/src/9/pc/vgaradeon.c
+++ b/sys/src/9/pc/vgaradeon.c
@@ -350,7 +350,7 @@
static void
radeondrawinit(VGAscr*scr)
{
- ulong bpp, dtype, i, pitch, clock_cntl_index, mclk_cntl, rbbm_soft_reset;
+ ulong dtype, i, clock_cntl_index, mclk_cntl, rbbm_soft_reset;
if (scr->mmio == 0)
return;
@@ -359,19 +359,15 @@
case 6:
case 8:
dtype = 2;
- bpp = 1;
break;
case 15:
dtype = 3;
- bpp = 2;
break;
case 16:
dtype = 4;
- bpp = 2;
break;
case 32:
dtype = 6;
- bpp = 4;
break;
default:
return;
@@ -413,11 +409,10 @@
radeonwaitfifo(scr, 1);
OUTREG(scr->mmio, RB2D_DSTCACHE_MODE, 0);
- pitch = Dx(scr->gscreen->r) * bpp;
radeonwaitfifo(scr, 4);
- OUTREG(scr->mmio, DEFAULT_PITCH, pitch);
- OUTREG(scr->mmio, DST_PITCH, pitch);
- OUTREG(scr->mmio, SRC_PITCH, pitch);
+ OUTREG(scr->mmio, DEFAULT_PITCH, scr->pitch);
+ OUTREG(scr->mmio, DST_PITCH, scr->pitch);
+ OUTREG(scr->mmio, SRC_PITCH, scr->pitch);
OUTREG(scr->mmio, DST_PITCH_OFFSET_C, 0);
radeonwaitfifo(scr, 3);
@@ -501,5 +496,4 @@
radeoncurdisable,
radeoncurload,
radeoncurmove,
- 0 /* doespanning */
};
--- a/sys/src/9/pc/vgas3.c
+++ b/sys/src/9/pc/vgas3.c
@@ -309,7 +309,7 @@
* Find a place for the cursor data in display memory.
* Must be on a 1024-byte boundary.
*/
- storage = (scr->gscreen->width*sizeof(ulong)*scr->gscreen->r.max.y+1023)/1024;
+ storage = (scr->pitch*scr->height+1023)/1024;
vgaxo(Crtx, 0x4C, storage>>8);
vgaxo(Crtx, 0x4D, storage & 0xFF);
storage *= 1024;
@@ -420,14 +420,12 @@
{
enum { Bitbltop = 0xCC }; /* copy source */
ulong *mmio;
- ulong cmd, stride;
+ ulong cmd;
Point dp, sp;
- int did, d;
+ int did;
- d = scr->gscreen->depth;
- did = (d-8)/8;
+ did = (scr->gscreen->depth-8)/8;
cmd = 0x00000020|(Bitbltop<<17)|(did<<2);
- stride = Dx(scr->gscreen->r)*d/8;
if(r.min.x <= sr.min.x){
cmd |= 1<<25;
@@ -452,7 +450,7 @@
waitforfifo(scr, 7);
mmio[SrcBase] = scr->paddr;
mmio[DstBase] = scr->paddr;
- mmio[Stride] = (stride<<16)|stride;
+ mmio[Stride] = (scr->pitch<<16)|scr->pitch;
mmio[WidthHeight] = ((Dx(r)-1)<<16)|Dy(r);
mmio[SrcXY] = (sp.x<<16)|sp.y;
mmio[DestXY] = (dp.x<<16)|dp.y;
@@ -466,13 +464,11 @@
{
enum { Bitbltop = 0xCC }; /* copy source */
ulong *mmio;
- ulong cmd, stride;
- int did, d;
+ ulong cmd;
+ int did;
- d = scr->gscreen->depth;
- did = (d-8)/8;
+ did = (scr->gscreen->depth-8)/8;
cmd = 0x16000120|(Bitbltop<<17)|(did<<2);
- stride = Dx(scr->gscreen->r)*d/8;
mmio = scr->mmio;
waitforlinearfifo(scr);
waitforfifo(scr, 8);
@@ -479,7 +475,7 @@
mmio[SrcBase] = scr->paddr;
mmio[DstBase] = scr->paddr;
mmio[DstBase] = scr->paddr;
- mmio[Stride] = (stride<<16)|stride;
+ mmio[Stride] = (scr->pitch<<16)|scr->pitch;
mmio[FgrdData] = sval;
mmio[WidthHeight] = ((Dx(r)-1)<<16)|Dy(r);
mmio[DestXY] = (r.min.x<<16)|r.min.y;
--- a/sys/src/9/pc/vgasavage.c
+++ b/sys/src/9/pc/vgasavage.c
@@ -540,7 +540,7 @@
/* set bitmap descriptors */
bd = (scr->gscreen->depth<<DepthShift) |
- (Dx(scr->gscreen->r)<<StrideShift) | BlockWriteDis
+ (scr->width<<StrideShift) | BlockWriteDis
| BDS64;
*(ulong*)(mmio+GBD1) = 0;
--- a/sys/src/9/pc/vgat2r4.c
+++ b/sys/src/9/pc/vgat2r4.c
@@ -459,14 +459,9 @@
static void
t2r4drawinit(VGAscr *scr)
{
- ulong pitch;
- int depth;
int fmt;
ulong *d;
- pitch = Dx(scr->gscreen->r);
- depth = scr->gscreen->depth;
-
switch(scr->gscreen->chan){
case RGB16:
fmt = 3;
@@ -488,8 +483,8 @@
d[BufCtl] = fmt<<24;
d[DeSorg] = 0;
d[DeDorg] = 0;
- d[DeSptch] = (pitch*depth)/8;
- d[DeDptch] = (pitch*depth)/8;
+ d[DeSptch] = scr->pitch;
+ d[DeDptch] = scr->pitch;
d[CmdClp] = 0; /* 2 = inside rectangle */
d[Mask] = ~0;
d[DeKey] = 0;