Commit Diff


commit - e63027eb68ff7252598003151d238dee8850ad34
commit + 012a8a02d5e43c1d4698acf42da61f4429c3ac1f
blob - 04931905d53b80a7217c68a41859426164ed42e3
blob + 18765bcd92158afcfc6259e5db73764d5792aa52
--- src/cmd/acme/acme.c
+++ src/cmd/acme/acme.c
@@ -67,6 +67,11 @@ threadmain(int argc, char *argv[])
 
 	loadfile = nil;
 	ARGBEGIN{
+	case 'D':
+		{extern int _threaddebuglevel;
+		_threaddebuglevel = ~0;
+		}
+		break;
 	case 'a':
 		globalautoindent = TRUE;
 		break;
@@ -643,6 +648,21 @@ waitthread(void *v)
 	alts[WCmd].op = CHANRCV;
 	alts[NWALT].op = CHANEND;
 
+	/*
+	 * BUG.  Actually there's no bug here but this is the
+	 * first place you'd look.  When a program is run,
+	 * it doesn't disappear from the main tag until the
+	 * mouse is moved or keyboard is hit.  This would
+	 * suggest that the WWait case isn't working right,
+	 * but what's actually going on is that the X11 code
+	 * is running a select-based threading loop that
+	 * doesn't get interrupted until there is data from X11.
+	 * This was done to make acme work on Suns and
+	 * other systems where our threading was sub-par.
+	 * Now that we've gotten pthreads working (sort of),
+	 * we might be able to fix this properly.
+	 * But the bug is in libdraw and libthread, not here.
+	 */
 	command = nil;
 	for(;;){
 		switch(alt(alts)){
blob - 2a3447425ae922a13ab668783f87b869e6af212c
blob + 4e31d6aef55064a1d64e72fbc4449e8546b471ba
--- src/cmd/acme/addr.c
+++ src/cmd/acme/addr.c
@@ -49,7 +49,7 @@ isregexc(int r)
 }
 
 Range
-number(Mntdir *md, Text *t, Range r, int line, int dir, int size, int *evalp)
+number(uint showerr, Text *t, Range r, int line, int dir, int size, int *evalp)
 {
 	uint q0, q1;
 
@@ -82,7 +82,7 @@ number(Mntdir *md, Text *t, Range r, int line, int dir
 		break;
 	case Fore:
 		if(q1 > 0)
-			while(textreadc(t, q1-1) != '\n')
+			while(q1<t->file->b.nc && textreadc(t, q1-1) != '\n')
 				q1++;
 		q0 = q1;
 		goto Forward;
@@ -107,7 +107,7 @@ number(Mntdir *md, Text *t, Range r, int line, int dir
 	return range(q0, q1);
 
     Rescue:
-	if(md != nil)
+	if(showerr)
 		warning(nil, "address out of range\n");
 	*evalp = FALSE;
 	return r;
@@ -115,14 +115,15 @@ number(Mntdir *md, Text *t, Range r, int line, int dir
 
 
 Range
-regexp(Mntdir *md, Text *t, Range lim, Range r, Rune *pat, int dir, int *foundp)
+regexp(uint showerr, Text *t, Range lim, Range r, Rune *pat, int dir, int *foundp)
 {
 	int found;
 	Rangeset sel;
 	int q;
 
 	if(pat[0] == '\0' && rxnull()){
-		warning(md, "no previous regular expression\n");
+		if(showerr)
+			warning(nil, "no previous regular expression\n");
 		*foundp = FALSE;
 		return r;
 	}
@@ -137,16 +138,17 @@ regexp(Mntdir *md, Text *t, Range lim, Range r, Rune *
 			q = Infinity;
 		else
 			q = lim.q1;
+warning(nil, "searching %d-%d\n", r.q1, q);
 		found = rxexecute(t, nil, r.q1, q, &sel);
 	}
-	if(!found && md==nil)
+	if(!found && showerr)
 		warning(nil, "no match for regexp\n");
 	*foundp = found;
 	return sel.r[0];
 }
 
 Range
-address(Mntdir *md, Text *t, Range lim, Range ar, void *a, uint q0, uint q1, int (*getc)(void*, uint),  int *evalp, uint *qp)
+address(uint showerr, Text *t, Range lim, Range ar, void *a, uint q0, uint q1, int (*getc)(void*, uint),  int *evalp, uint *qp)
 {
 	int dir, size, npat;
 	int prevc, c, nc, n;
@@ -175,7 +177,7 @@ address(Mntdir *md, Text *t, Range lim, Range ar, void
 			if(q>=q1 && t!=nil && t->file!=nil)	/* rhs defaults to $ */
 				r.q1 = t->file->b.nc;
 			else{
-				nr = address(md, t, lim, ar, a, q, q1, getc, evalp, &q);
+				nr = address(showerr, t, lim, ar, a, q, q1, getc, evalp, &q);
 				r.q1 = nr.q1;
 			}
 			*qp = q;
@@ -184,7 +186,7 @@ address(Mntdir *md, Text *t, Range lim, Range ar, void
 		case '-':
 			if(*evalp && (prevc=='+' || prevc=='-'))
 				if((nc=(*getc)(a, q))!='#' && nc!='/' && nc!='?')
-					r = number(md, t, r, 1, prevc, Line, evalp);	/* do previous one */
+					r = number(showerr, t, r, 1, prevc, Line, evalp);	/* do previous one */
 			dir = c;
 			break;
 		case '.':
@@ -222,7 +224,7 @@ address(Mntdir *md, Text *t, Range lim, Range ar, void
 				n = n*10+(c-'0');
 			}
 			if(*evalp)
-				r = number(md, t, r, n, dir, size, evalp);
+				r = number(showerr, t, r, n, dir, size, evalp);
 			dir = None;
 			size = Line;
 			break;
@@ -255,7 +257,7 @@ address(Mntdir *md, Text *t, Range lim, Range ar, void
 			pat = runerealloc(pat, npat+1);
 			pat[npat] = 0;
 			if(*evalp)
-				r = regexp(md, t, lim, r, pat, dir, evalp);
+				r = regexp(showerr, t, lim, r, pat, dir, evalp);
 			free(pat);
 			dir = None;
 			size = Line;
@@ -263,7 +265,7 @@ address(Mntdir *md, Text *t, Range lim, Range ar, void
 		}
 	}
 	if(*evalp && dir != None)
-		r = number(md, t, r, 1, dir, Line, evalp);	/* do previous one */
+		r = number(showerr, t, r, 1, dir, Line, evalp);	/* do previous one */
 	*qp = q;
 	return r;
 }
blob - fe4b060116e86ba1c0c733dbe2f0bc5997e77ffd
blob + 48a57dd2ccb543b92a6eff51e3c6091694361a02
--- src/cmd/acme/dat.h
+++ src/cmd/acme/dat.h
@@ -19,6 +19,7 @@ enum
 	QWrdsel,
 	QWwrsel,
 	QWtag,
+	QWxdata,
 	QMAX,
 };
 
@@ -30,6 +31,7 @@ enum
 	Infinity = 		0x7FFFFFFF,	/* huge value for regexp address */
 };
 
+#define Buffer AcmeBuffer
 typedef	struct	Block Block;
 typedef	struct	Buffer Buffer;
 typedef	struct	Command Command;
blob - 37d5edaef99f81d70e922c7197a0be61c31ef922
blob + 85ef69a5a236086eedd71c50818c41e66bc1b73c
--- src/cmd/acme/exec.c
+++ src/cmd/acme/exec.c
@@ -342,7 +342,7 @@ delcol(Text *et, Text *_0, Text *_1, int _2, int _3, R
 		return;
 	for(i=0; i<c->nw; i++){
 		w = c->w[i];
-		if(w->nopen[QWevent]+w->nopen[QWaddr]+w->nopen[QWdata] > 0){
+		if(w->nopen[QWevent]+w->nopen[QWaddr]+w->nopen[QWdata]+w->nopen[QWxdata] > 0){
 			warning(nil, "can't delete column; %.*S is running an external command\n", w->body.file->nname, w->body.file->name);
 			return;
 		}
@@ -1528,7 +1528,7 @@ Hard:
 	if(ret >= 0){
 		if(cpid)
 			sendul(cpid, ret);
-		threadexits("");
+		threadexits(nil);
 	}
 	warning(nil, "exec rc: %r\n");
 
blob - 2257d681a094ea3569e7af968285b005d7bf5d21
blob + c61f96ecf1b98ca54e502ab525e08176d38f82c9
--- src/cmd/acme/fns.h
+++ src/cmd/acme/fns.h
@@ -81,7 +81,7 @@ int		isregexc(int);
 void *emalloc(uint);
 void *erealloc(void*, uint);
 char	*estrdup(char*);
-Range		address(Mntdir*, Text*, Range, Range, void*, uint, uint, int (*)(void*, uint),  int*, uint*);
+Range		address(uint, Text*, Range, Range, void*, uint, uint, int (*)(void*, uint),  int*, uint*);
 int		rxexecute(Text*, Rune*, uint, uint, Rangeset*);
 int		rxbexecute(Text*, uint, Rangeset*);
 Window*	makenewwindow(Text *t);
blob - 50e63411d4b39db2064990439f90fcdadadaa1df
blob + a095529f8e2b49ce4320db78e2efe1686b4866dc
--- src/cmd/acme/fsys.c
+++ src/cmd/acme/fsys.c
@@ -87,6 +87,7 @@ Dirtab dirtabw[]=
 	{ "rdsel",		QTFILE,		QWrdsel,		0400 },
 	{ "wrsel",		QTFILE,		QWwrsel,		0200 },
 	{ "tag",		QTAPPEND,	QWtag,		0600|DMAPPEND },
+	{ "xdata",		QTFILE,		QWxdata,		0600 },
 	{ nil, }
 };
 
blob - f892640a27e28e1daceefd8555e14051fbafa9aa
blob + d760745df6ff9e212145eb331c70e0b4fffa4b10
--- src/cmd/acme/look.c
+++ src/cmd/acme/look.c
@@ -591,7 +591,7 @@ expandfile(Text *t, uint q0, uint q1, Expand *e)
 	e->u.at = t;
 	e->a0 = amin+1;
 	eval = FALSE;
-	address(nil, nil, range(-1,-1), range(0,0), t, e->a0, amax, tgetc, &eval, (uint*)&e->a1);
+	address(TRUE, nil, range(-1,-1), range(0,0), t, e->a0, amax, tgetc, &eval, (uint*)&e->a1);
 	return TRUE;
 
    Isntfile:
@@ -723,7 +723,7 @@ openfile(Text *t, Expand *e)
 		eval = FALSE;
 	else{
 		eval = TRUE;
-		r = address(nil, t, range(-1,-1), range(t->q0, t->q1), e->u.at, e->a0, e->a1, e->agetc, &eval, &dummy);
+		r = address(TRUE, t, range(-1,-1), range(t->q0, t->q1), e->u.at, e->a0, e->a1, e->agetc, &eval, &dummy);
 		if(eval == FALSE)
 			e->jump = FALSE;	/* don't jump if invalid address */
 	}
blob - 5fc4c5a5d24ba932dfef98cdf26fd08373973bb1
blob + 5a2723a435c39423ed578013eff80032c951f32b
--- src/cmd/acme/xfid.c
+++ src/cmd/acme/xfid.c
@@ -103,13 +103,8 @@ xfidopen(Xfid *x)
 		q = FILE(x->f->qid);
 		switch(q){
 		case QWaddr:
-			if(w->nopen[q]++ == 0){
-				w->addr = range(0,0);
-				w->limit = range(-1,-1);
-			}
-			break;
-		case QWdata:
-			w->nopen[q]++;
+			w->nopen[q]++;
+			w->limit = range(-1,-1);
 			break;
 		case QWevent:
 			if(w->nopen[q]++ == 0){
@@ -214,12 +209,13 @@ xfidclose(Xfid *x)
 			}
 			break;
 		case QWdata:
+		case QWxdata:
 			w->nomark = FALSE;
 			/* fall through */
 		case QWaddr:
 		case QWevent:	/* BUG: do we need to shut down Xfid? */
 			if(--w->nopen[q] == 0){
-				if(q == QWdata)
+				if(q == QWdata || q == QWxdata)
 					w->nomark = FALSE;
 				if(q==QWevent && !w->isdir && w->col!=nil){
 					w->filemenu = TRUE;
@@ -327,6 +323,15 @@ xfidread(Xfid *x)
 		w->addr.q1 = w->addr.q0;
 		break;
 
+	case QWxdata:
+		/* BUG: what should happen if q1 > q0? */
+		if(w->addr.q0 > w->body.file->b.nc){
+			respond(x, &fc, Eaddr);
+			break;
+		}
+		w->addr.q0 += xfidruneread(x, &w->body, w->addr.q0, w->addr.q1);
+		break;
+
 	case QWtag:
 		xfidutfread(x, &w->tag, w->tag.file->b.nc, QWtag);
 		break;
@@ -398,7 +403,7 @@ xfidwrite(Xfid *x)
 		t = &w->body;
 		wincommit(w, t);
 		eval = TRUE;
-		a = address(x->f->mntdir, t, w->limit, w->addr, r, 0, nr, rgetc, &eval, (uint*)&nb);
+		a = address(FALSE, t, w->limit, w->addr, r, 0, nr, rgetc, &eval, (uint*)&nb);
 		free(r);
 		if(nb < nr){
 			respond(x, &fc, Ebadaddr);