shithub: riscv

Download patch

ref: 219050cc36b169a1f55b5441553bc8e123ddfa7e
parent: db729cbb50a43ed357ac8153b8a9717684aa6f4b
author: cinap_lenrek <[email protected]>
date: Tue Apr 18 21:46:20 EDT 2017

vt: make it fast

--- a/sys/src/cmd/vt/cons.h
+++ b/sys/src/cmd/vt/cons.h
@@ -10,8 +10,8 @@
 
 #define	INSET	2
 #define	BUFS	32
-#define	HISTSIZ	65536	/* number of history characters */
-#define BSIZE	1000
+#define	HISTSIZ	(64*1024)	/* number of history characters */
+#define BSIZE	(8*1024)
 
 #define	SCROLL	2
 #define NEWLINE	1
@@ -22,17 +22,13 @@
 
 /* text attributes */
 enum {
-	THighIntensity = (1<<0),
-	TUnderline = (1<<1),
-	TBlink = (1<<2),
-	TReverse = (1<<3),
-	TInvisible = (1<<4),
+	THighIntensity = 1<<0,
+	TUnderline = 1<<1,
+	TBlink = 1<<2,
+	TReverse = 1<<3,
+	TInvisible = 1<<4,
 };
 
-#define	button1()	((mouse.buttons & 07)==1)
-#define	button2()	((mouse.buttons & 07)==2)
-#define	button3()	((mouse.buttons & 07)==4)
-
 struct ttystate {
 	int	crnl;
 	int	nlcr;
@@ -64,9 +60,8 @@
 extern Point	pt(int, int);
 extern Point	pos(Point);
 extern void	funckey(int);
-extern void	drawstring(Rune*, int, int);
+extern void	drawstring(Rune*, int);
 
-extern int	debug;
 extern int	yscrmin, yscrmax;
 extern int	attr;
 extern int	defattr;
@@ -75,13 +70,9 @@
 extern Image *bgcolor;
 extern Image *colors[];
 extern Image *hicolors[];
-extern Image *bgdefault;
-extern Image *fgdefault;
 
 extern int cursoron;
 extern int nocolor;
 
-extern void curson(void);
-extern void cursoff(void);
 extern void setdim(int, int);
 
--- a/sys/src/cmd/vt/main.c
+++ b/sys/src/cmd/vt/main.c
@@ -44,13 +44,13 @@
 Menu	menu3;
 Rune	*histp;
 Rune	hist[HISTSIZ];
-Rune	*onscreen;
+Rune	*onscreenrbuf;
+uchar	*onscreenabuf;
+uchar	*onscreencbuf;
 int	yscrmin, yscrmax;
 int	attr, defattr;
-int	wctlout;
 
 Image	*bordercol;
-Image	*cursback;
 Image	*colors[8];
 Image	*hicolors[8];
 Image	*red;
@@ -57,8 +57,6 @@
 Image	*green;
 Image	*fgcolor;
 Image	*bgcolor;
-Image	*fgdefault;
-Image	*bgdefault;
 Image	*highlight;
 
 uint rgbacolors[8] = {
@@ -91,15 +89,17 @@
 int	XMARGIN;
 int	YMARGIN;
 
-Mouse	mouse;
 Rune	kbdchar;
 
+#define	button1()	((mc->buttons & 07)==1)
+#define	button2()	((mc->buttons & 07)==2)
+#define	button3()	((mc->buttons & 07)==4)
+
 Mousectl	*mc;
 Keyboardctl	*kc;
 Channel		*hc;
 Consstate	*cs;
 
-int	debug;
 int	nocolor;
 int	logfd = -1;
 int	hostfd = -1;
@@ -126,7 +126,6 @@
 void	send_interrupt(void);
 int	alnum(int);
 void	escapedump(int,uchar *,int);
-Rune*	onscreenp(int, int);
 
 int
 start_host(void)
@@ -219,6 +218,7 @@
 	fk = vt100fk;
 	blkbg = nocolor = 0;
 	rflag = 0;
+	attr = defattr;
 	ARGBEGIN{
 	case '2':
 		term = "vt220";
@@ -276,7 +276,6 @@
 	red = allocimage(display, Rect(0,0,1,1), screen->chan, 1, DRed);
 	green = allocimage(display, Rect(0,0,1,1), screen->chan, 1, DGreen);
 	bordercol = allocimage(display, Rect(0,0,1,1), screen->chan, 1, 0xCCCCCCCC);
-	cursback = allocimage(display, Rect(0, 0, CW+1, NS+1), screen->chan, 0, DNofill);
 	highlight = allocimage(display, Rect(0,0,1,1), CHAN1(CAlpha,8), 1, 0x80);
 
 	for(i=0; i<8; i++){
@@ -285,15 +284,11 @@
 		hicolors[i] = allocimage(display, Rect(0,0,1,1), screen->chan, 1,
 			rgbahicolors[i]);
 	}
-
-	bgdefault = (blkbg? display->black: display->white);
-	fgdefault = (blkbg? display->white: display->black);
-	bgcolor = bgdefault;
-	fgcolor = fgdefault;
-
+	bgcolor = (blkbg? display->black: display->white);
+	fgcolor = (blkbg? display->white: display->black);
 	resize();
 
-	hc = chancreate(sizeof(Rune*), 1);
+	hc = chancreate(sizeof(Rune*), 5);
 	if((hostfd = start_host()) >= 0)
 		proccreate(hostreader, nil, BSIZE+1024);
 
@@ -308,15 +303,81 @@
 	}
 }
 
+#define onscreenr(x, y) &onscreenrbuf[((y)*(xmax+2) + (x))]
+#define onscreena(x, y) &onscreenabuf[((y)*(xmax+2) + (x))]
+#define onscreenc(x, y) &onscreencbuf[((y)*(xmax+2) + (x))]
+
+#define bgcol(a, c) (((a)&TReverse)!=0 ? (c)>>4 : (c&15))
+#define fgcol(a, c) ((((a)&TReverse)==0 ? (c)>>4 : (c&15)) | (((a)&THighIntensity)!=0)<<4)
+
 void
+drawscreen(void)
+{
+	int x, y, n;
+	uchar c, *ap, *cp;
+	Rune *rp;
+	Point p;
+
+	/* draw background */
+	draw(screen, screen->r, bgcolor, nil, ZP);
+	for(y = 0; y <= ymax; y++){
+		for(x = 0; x <= xmax; x += n){
+			cp = onscreenc(x, y);
+			if((*cp & 1) == 0){
+				n = 1;
+				continue;
+			}
+			ap = onscreena(x, y);
+			c = bgcol(*ap, *cp);
+			for(n = 1; x+n <= xmax && bgcol(ap[n], cp[n]) == c; n++)
+				;
+			p = pt(x, y);
+			draw(screen, Rpt(p, Pt(p.x+CW, p.y+NS)), colors[c>>1], nil, ZP);
+		}
+	}
+
+	/* draw foreground */
+	for(y = 0; y <= ymax; y++){
+		for(x = 0; x <= xmax; x += n){
+			rp = onscreenr(x, y);
+			if(*rp == 0){
+				n = 1;
+				continue;
+			}
+			ap = onscreena(x, y);
+			cp = onscreenc(x, y);
+			c = fgcol(*ap, *cp);
+			for(n = 1; x+n <= xmax && rp[n] != 0 && fgcol(ap[n], cp[n]) == c; n++)
+				;
+			runestringn(screen, pt(x, y),
+				(c&1) ? (((c&16) ? hicolors : colors)[(c&15)>>1]) : fgcolor,
+				ZP, font, rp, n);
+		}
+		if(*onscreenr(x, y) == 0)
+			runestringn(screen, pt(x, y),
+				bordercol,
+				ZP, font, L">", 1);
+	}
+}
+
+void
+drawcursor(void)
+{
+	Image *col = (blocked || hostfd < 0) ? red : bordercol;
+	border(screen, Rpt(pt(x, y), pt(x+1, y+1)), 2, col, ZP);
+}
+
+void
 clear(int x1, int y1, int x2, int y2)
 {
-	draw(screen, Rpt(pt(x1,y1), pt(x2,y2)), bgcolor, nil, ZP);
 	while(y1 < y2){
-		if(x1 < x2)
-			memset(onscreenp(x1, y1), 0, (x2-x1)*sizeof(Rune));
+		if(x1 < x2){
+			memset(onscreenr(x1, y1), 0, (x2-x1)*sizeof(Rune));
+			memset(onscreena(x1, y1), 0, x2-x1);
+			memset(onscreenc(x1, y1), 0, x2-x1);
+		}
 		if(x2 > xmax)
-			*onscreenp(xmax+1, y1) = '\n';
+			*onscreenr(xmax+1, y1) = '\n';
 		y1++;
 	}
 }
@@ -325,7 +386,7 @@
 newline(void)
 {
 	if(x > xmax)
-		*onscreenp(xmax+1, y) = 0;	/* wrap arround, remove hidden newline */
+		*onscreenr(xmax+1, y) = 0;	/* wrap arround, remove hidden newline */
 	nbacklines--;
 	if(y >= yscrmax) {
 		y = yscrmax;
@@ -339,25 +400,6 @@
 	olines++;
 }
 
-void
-cursoff(void)
-{
-	draw(screen, Rpt(pt(x, y), addpt(pt(x, y), Pt(CW,NS))), cursback, nil, cursback->r.min);
-}
-
-void
-curson(void)
-{
-	Image *col = (blocked || hostfd < 0) ? red : bordercol;
-
-	if(!cursoron){
-		cursoff();
-		return;
-	}
-	draw(cursback, cursback->r, screen, nil, pt(x, y));
-	border(screen, Rpt(pt(x, y), addpt(pt(x, y), Pt(CW,NS))), 2, col, ZP);
-}
-
 int
 get_next_char(void)
 {
@@ -602,8 +644,12 @@
 			if(host_avail())
 				return(rcvchar());
 			free(hostbuf);
-			hostbuf = hostbufp = nil;
+			hostbufp = hostbuf = nbrecvp(hc);
+			if(host_avail())
+				return(rcvchar());
 		}
+		drawscreen();
+		drawcursor();
 		waitio();
 	}
 }
@@ -613,17 +659,16 @@
 {
 	enum { AMOUSE, ARESIZE, AKBD, AHOST, AEND, };
 	Alt a[AEND+1] = {
-		{ mc->c, &mouse, CHANRCV },
+		{ mc->c, &mc->Mouse, CHANRCV },
 		{ mc->resizec, nil, CHANRCV },
 		{ kc->c, &kbdchar, CHANRCV },
 		{ hc, &hostbuf, CHANNOP },
 		{ nil, nil, CHANEND },
 	};
-
 	if(hostbuf == nil) a[AHOST].op = CHANRCV;
-
-	curson();	/* turn on cursor while we're waiting */
-	flushimage(display, 1);
+Next:
+	if(display->bufp > display->buf)
+		flushimage(display, 1);
 	switch(alt(a)){
 	case AMOUSE:
 		if(button1())
@@ -630,6 +675,8 @@
 			selection();
 		else if(button2() || button3())
 			readmenu();
+		else if(resize_flag == 0)
+			goto Next;
 		break;
 	case ARESIZE:
 		resize_flag = 2;
@@ -636,13 +683,12 @@
 		break;
 	case AHOST:
 		hostbufp = hostbuf;
-		if(hostbufp == nil){
+		if(hostbuf == nil){
 			close(hostfd);
 			hostfd = -1;
 		}
 		break;
 	}
-	cursoff();	/* turn cursor back off */
 }
 
 void
@@ -681,9 +727,14 @@
 	yscrmax = ymax;
 	olines = 0;
 	exportsize();
-	free(onscreen);
-	onscreen = mallocz((ymax+1)*(xmax+2)*sizeof(Rune), 1);
-	border(screen, screen->r, XMARGIN+YMARGIN, bgcolor, ZP);
+
+	free(onscreenrbuf);
+	onscreenrbuf = mallocz((ymax+1)*(xmax+2)*sizeof(Rune), 1);
+	free(onscreenabuf);
+	onscreenabuf = mallocz((ymax+1)*(xmax+2), 1);
+	free(onscreencbuf);
+	onscreencbuf = mallocz((ymax+1)*(xmax+2), 1);
+
 	clear(0,0,xmax+1,ymax+1);
 	if(resize_flag > 1)
 		backup(backc);
@@ -694,20 +745,18 @@
 void
 setdim(int ht, int wid)
 {
-	int fd;
 	Rectangle r;
+	int fd;
 
-	if(ht != -1)
-		ymax = ht-1;
-	if(wid != -1)
-		xmax = wid-1;
+	if(wid <= 0) wid = xmax+1;
+	if(ht <= 0) ht = ymax+1;
 	r.min = screen->r.min;
-	r.max = addpt(screen->r.min, Pt((xmax+1)*CW+2*INSET, (ymax+1)*NS+2*INSET));
+	r.max = addpt(screen->r.min, Pt(wid*CW+2*INSET, ht*NS+2*INSET));
 	fd = open("/dev/wctl", OWRITE);
-	if(fd < 0 || fprint(fd, "resize -dx %d -dy %d\n", Dx(r)+2*Borderwidth, Dy(r)+2*Borderwidth) < 0)
-		resize();
-	if(fd >= 0)
+	if(fd >= 0){
+		fprint(fd, "resize -dx %d -dy %d\n", Dx(r)+2*Borderwidth, Dy(r)+2*Borderwidth);
 		close(fd);
+	}
 }
 
 void
@@ -769,10 +818,10 @@
 
 	backup = allocimage(display, screen->r, screen->chan, 0, DNofill);
 	draw(backup, backup->r, screen, nil, backup->r.min);
-	p = pos(mouse.xy);
+	p = pos(mc->xy);
 	do {
-		q = pos(mouse.xy);
-		if(onscreenp(p.x, p.y) > onscreenp(q.x, q.y)){
+		q = pos(mc->xy);
+		if(onscreenr(p.x, p.y) > onscreenr(q.x, q.y)){
 			r.min = q;
 			r.max = p;
 		} else {
@@ -784,12 +833,11 @@
 		d = drawselection(r, ZR, red);
 		flushimage(display, 1);
 		readmouse(mc);
-		mouse = mc->Mouse;
 		draw(screen, d, backup, nil, d.min);
 	} while(button1());
-	if((mouse.buttons & 07) == 5)
+	if((mc->buttons & 07) == 5)
 		sendsnarf();
-	else if(writesnarf(onscreenp(r.min.x, r.min.y), onscreenp(r.max.x, r.max.y))){
+	else if(writesnarf(onscreenr(r.min.x, r.min.y), onscreenr(r.max.x, r.max.y))){
 		d = drawselection(r, ZR, green);
 		flushimage(display, 1);
 		sleep(200);
@@ -924,17 +972,12 @@
 	return pt;
 }
 
-Rune*
-onscreenp(int x, int y)
-{
-	return onscreen + (y*(xmax+2) + x);
-}
-
 void
 scroll(int sy, int ly, int dy, int cy)	/* source, limit, dest, which line to clear */
 {
-	memmove(onscreenp(0, dy), onscreenp(0, sy), (ly-sy)*(xmax+2)*sizeof(Rune));
-	draw(screen, Rpt(pt(0, dy), pt(xmax+1, dy+ly-sy)), screen, nil, pt(0, sy));
+	memmove(onscreenr(0, dy), onscreenr(0, sy), (ly-sy)*(xmax+2)*sizeof(Rune));
+	memmove(onscreena(0, dy), onscreena(0, sy), (ly-sy)*(xmax+2));
+	memmove(onscreenc(0, dy), onscreenc(0, sy), (ly-sy)*(xmax+2));
 	clear(0, cy, xmax+1, cy+1);
 }
 
@@ -950,8 +993,9 @@
 		x = y = 0;
 		return;
 	}
-	draw(screen, Rpt(pt(0, 0), pt(xmax+1, ymax+1)), screen, nil, pt(0, half));
-	memmove(onscreenp(0, 0), onscreenp(0, half), (ymax-half+1)*(xmax+2)*sizeof(Rune));
+	memmove(onscreenr(0, 0), onscreenr(0, half), (ymax-half+1)*(xmax+2)*sizeof(Rune));
+	memmove(onscreena(0, 0), onscreena(0, half), (ymax-half+1)*(xmax+2));
+	memmove(onscreenc(0, 0), onscreenc(0, half), (ymax-half+1)*(xmax+2));
 	clear(0, y-half+1, xmax+1, ymax+1);
 	y -= half;
 	if(olines)
@@ -992,7 +1036,9 @@
 {
 	if(*echop != 0 && fullrune(echop, strlen(echop)))
 		return 1;
-	return hostbufp != nil && *hostbufp != 0;
+	if(hostbuf == nil)
+		return 0;
+	return *hostbufp != 0;
 }
 
 int
@@ -1051,28 +1097,10 @@
 	sendnchars(strlen(fk[key].sequence), fk[key].sequence);
 }
 
-
 void
-drawstring(Rune *str, int n, int attr)
+drawstring(Rune *str, int n)
 {
-	int i;
-	Image *txt, *bg, *tmp;
-	Point p;
-
-	txt = fgcolor;
-	bg = bgcolor;
-	if(attr & TReverse){
-		tmp = txt;
-		txt = bg;
-		bg = tmp;
-	}
-	if(attr & THighIntensity){
-		for(i=0; i<8; i++)
-			if(txt == colors[i])
-				txt = hicolors[i];
-	}
-	p = pt(x, y);
-	draw(screen, Rpt(p, addpt(p, runestringsize(font, str))), bg, nil, p);
-	runestring(screen, p, txt, ZP, font, str);
-	memmove(onscreenp(x, y), str, n*sizeof(Rune));
+	memmove(onscreenr(x, y), str, n*sizeof(Rune));
+	memset(onscreena(x, y), attr & 0xFF, n);
+	memset(onscreenc(x, y), attr >> 8, n);
 }
--- a/sys/src/cmd/vt/vt.c
+++ b/sys/src/cmd/vt/vt.c
@@ -143,7 +143,6 @@
 	int savex, savey, saveattr, saveisgraphics;
 	int isgraphics;
 	int g0set, g1set;
-	int dch;
 
 	isgraphics = 0;
 	g0set = 'B';	/* US ASCII */
@@ -237,7 +236,7 @@
 			break;
 
 		case '\033':
-			switch(dch = get_next_char()){
+			switch(get_next_char()){
 			/*
 			 * 1 - graphic processor option on (no-op; not installed)
 			 */
@@ -254,7 +253,6 @@
 			 * 7 - save cursor position.
 			 */
 			case '7':
-//print("save\n");
 				savex = x;
 				savey = y;
 				saveattr = attr;
@@ -265,7 +263,6 @@
 			 * 8 - restore cursor position.
 			 */
 			case '8':
-//print("restore\n");
 				x = savex;
 				y = savey;
 				attr = saveattr;
@@ -276,7 +273,6 @@
 			 * c - Reset terminal.
 			 */
 			case 'c':
-print("resetterminal\n");
 				cursoron = 1;
 				ttystate[cs->raw].nlcr = 0;
 				break;
@@ -401,7 +397,7 @@
 				/*
 				 * do escape2 stuff
 				 */
-				switch(dch = buf[0]){
+				switch(buf[0]){
 					/*
 					 * c - same as ESC Z: what are you?
 					 */
@@ -803,13 +799,6 @@
 							break;
 						}
 						break;
-
-					/*
-					 * Anything else we ignore for now...
-					 */
-					default:
-print("unknown escape2 '%c' (0x%x)\n", dch, dch);
-						break;
 				}
 
 				break;
@@ -825,14 +814,6 @@
 			case ']':
 				osc();
 				break;
-
-			/*
-			 * Ignore other commands.
-			 */
-			default:
-print("unknown command '%c' (0x%x)\n", dch, dch);
-				break;
-
 			}
 			break;
 
@@ -858,7 +839,7 @@
 				c = 0;
 			}
 			buf[n] = 0;
-			drawstring(buf, n, attr);
+			drawstring(buf, n);
 			x += n;
 			peekc = c;
 			break;
@@ -875,8 +856,6 @@
 		switch(argv[i]) {
 		case 0:
 			attr = defattr;
-			fgcolor = fgdefault;
-			bgcolor = bgdefault;
 			break;
 		case 1:
 			attr |= THighIntensity;
@@ -916,10 +895,10 @@
 		case 35:	/* purple */
 		case 36:	/* cyan */
 		case 37:	/* white */
-			fgcolor = (nocolor? fgdefault: colors[argv[i]-30]);
+			attr = (attr & ~0xF000) | 0x1000 | (argv[i]-30)<<13;
 			break;
-		case 39:
-			fgcolor = fgdefault;
+		case 39:	/* default */
+			attr &= ~0xF000;
 			break;
 		case 40:	/* black */
 		case 41:	/* red */
@@ -929,10 +908,10 @@
 		case 45:	/* purple */
 		case 46:	/* cyan */
 		case 47:	/* white */
-			bgcolor = (nocolor? bgdefault: colors[argv[i]-40]);
+			attr = (attr & ~0x0F00) | 0x0100 | (argv[i]-40)<<9;
 			break;
-		case 49:
-			bgcolor = bgdefault;
+		case 49:	/* default */
+			attr &= ~0x0F00;
 			break;
 		}
 	}
@@ -964,9 +943,6 @@
 				fprint(fd, "%S", buf);
 				close(fd);
 			}
-			break;
-		default:
-			fprint(2, "unknown osc escape %d\n", osc);
 			break;
 		}
 	}