diff options
author | Petter Rodhelind <petter.rodhelind@gmail.com> | 2019-07-20 15:34:42 +0200 |
---|---|---|
committer | Petter Rodhelind <petter.rodhelind@gmail.com> | 2019-07-20 15:34:42 +0200 |
commit | 618fef785e57e971f26fc984df1adb5807a521fe (patch) | |
tree | 4d05f2274e4b993538dc0e53f621ad14de7ab16f /src/cmd/acme | |
parent | 6d98adb7f4139424b57ab1ea9caa521691ae83fa (diff) | |
parent | e995a0c101863688d5f14649ae3de45a7c43789c (diff) | |
download | plan9port-618fef785e57e971f26fc984df1adb5807a521fe.tar.gz plan9port-618fef785e57e971f26fc984df1adb5807a521fe.tar.bz2 plan9port-618fef785e57e971f26fc984df1adb5807a521fe.zip |
Merge remote-tracking branch 'upstream/master'
Diffstat (limited to 'src/cmd/acme')
-rw-r--r-- | src/cmd/acme/exec.c | 105 | ||||
-rw-r--r-- | src/cmd/acme/look.c | 48 |
2 files changed, 103 insertions, 50 deletions
diff --git a/src/cmd/acme/exec.c b/src/cmd/acme/exec.c index 290e0514..bb2c93d6 100644 --- a/src/cmd/acme/exec.c +++ b/src/cmd/acme/exec.c @@ -695,42 +695,10 @@ checksha1(char *name, File *f, Dir *d) } } -static uint -trimspaces(Rune *r, uint *np, int eof) -{ - uint i, w, nonspace, n; - Rune c; - - nonspace = 0; - w = 0; - n = *np; - for(i=0; i<n; i++) { - c = r[i]; - if(c == '\n') - w = nonspace; - r[w++] = c; - if(c != ' ' && c != '\t') - nonspace = w; - } - if(nonspace > 0 && nonspace < w) { - // Trailing spaces at end of buffer. - // Tell caller to reread them with what follows, - // so we can determine whether they need trimming. - // Unless the trailing spaces are the entire buffer, - // in which case let them through to avoid an infinite loop - // if an entire buffer fills with spaces. - // At EOF, just consume the spaces. - if(!eof) - *np = n - (w - nonspace); - w = nonspace; - } - return w; -} - void putfile(File *f, int q0, int q1, Rune *namer, int nname) { - uint n, nn, m; + uint n, m; Rune *r; Biobuf *b; char *s, *name; @@ -757,6 +725,7 @@ putfile(File *f, int q0, int q1, Rune *namer, int nname) goto Rescue1; } } + fd = create(name, OWRITE, 0666); if(fd < 0){ warning(nil, "can't create file %s: %r\n", name); @@ -785,14 +754,7 @@ putfile(File *f, int q0, int q1, Rune *namer, int nname) if(n > BUFSIZE/UTFmax) n = BUFSIZE/UTFmax; bufread(&f->b, q, r, n); - nn = n; - // An attempt at automatically trimming trailing spaces. - // Breaks programs that inspect body file and think it will match on-disk file - // when window is clean. Should apply the changes to the actual window instead. - // Later. - if(0 && w->autoindent) - nn = trimspaces(r, &n, q+n==q1); - m = snprint(s, BUFSIZE+1, "%.*S", nn, r); + m = snprint(s, BUFSIZE+1, "%.*S", n, r); sha1((uchar*)s, m, nil, h); if(Bwrite(b, s, m) != m){ warning(nil, "can't write file %s: %r\n", name); @@ -871,6 +833,65 @@ putfile(File *f, int q0, int q1, Rune *namer, int nname) free(name); } +static void +trimspaces(Text *et) +{ + File *f; + Rune *r; + Text *t; + uint q0, n, delstart; + int c, i, marked; + + t = &et->w->body; + f = t->file; + marked = 0; + + if(t->w!=nil && et->w!=t->w){ + /* can this happen when t == &et->w->body? */ + c = 'M'; + if(et->w) + c = et->w->owner; + winlock(t->w, c); + } + + r = fbufalloc(); + q0 = f->b.nc; + delstart = q0; /* end of current space run, or 0 if no active run; = q0 to delete spaces before EOF */ + while(q0 > 0) { + n = RBUFSIZE; + if(n > q0) + n = q0; + q0 -= n; + bufread(&f->b, q0, r, n); + for(i=n; ; i--) { + if(i == 0 || (r[i-1] != ' ' && r[i-1] != '\t')) { + // Found non-space or start of buffer. Delete active space run. + if(q0+i < delstart) { + if(!marked) { + marked = 1; + seq++; + filemark(f); + } + textdelete(t, q0+i, delstart, TRUE); + } + if(i == 0) { + /* keep run active into tail of next buffer */ + if(delstart > 0) + delstart = q0; + break; + } + delstart = 0; + if(r[i-1] == '\n') + delstart = q0+i-1; /* delete spaces before this newline */ + } + } + } + fbuffree(r); + + if(t->w!=nil && et->w!=t->w) + winunlock(t->w); +} + void put(Text *et, Text *_0, Text *argt, int _1, int _2, Rune *arg, int narg) { @@ -893,6 +914,8 @@ put(Text *et, Text *_0, Text *argt, int _1, int _2, Rune *arg, int narg) warning(nil, "no file name\n"); return; } + if(w->autoindent) + trimspaces(et); namer = bytetorune(name, &nname); putfile(f, 0, f->b.nc, namer, nname); xfidlog(w, "put"); diff --git a/src/cmd/acme/look.c b/src/cmd/acme/look.c index cbbc71bf..44e23cca 100644 --- a/src/cmd/acme/look.c +++ b/src/cmd/acme/look.c @@ -30,7 +30,7 @@ plumbthread(void *v) USED(v); threadsetname("plumbproc"); - + /* * Loop so that if plumber is restarted, acme need not be. */ @@ -46,7 +46,7 @@ plumbthread(void *v) } plumbeditfid = fid; plumbsendfid = plumbopenfid("send", OWRITE|OCEXEC); - + /* * Relay messages. */ @@ -432,9 +432,9 @@ includename(Text *t, Rune *r, int n) char buf[128]; Rune Lsysinclude[] = { '/', 's', 'y', 's', '/', 'i', 'n', 'c', 'l', 'u', 'd', 'e', 0 }; Rune Lusrinclude[] = { '/', 'u', 's', 'r', '/', 'i', 'n', 'c', 'l', 'u', 'd', 'e', 0 }; - Rune Lusrlocalinclude[] = { '/', 'u', 's', 'r', '/', 'l', 'o', 'c', 'a', 'l', + Rune Lusrlocalinclude[] = { '/', 'u', 's', 'r', '/', 'l', 'o', 'c', 'a', 'l', '/', 'i', 'n', 'c', 'l', 'u', 'd', 'e', 0 }; - Rune Lusrlocalplan9include[] = { '/', 'u', 's', 'r', '/', 'l', 'o', 'c', 'a', 'l', + Rune Lusrlocalplan9include[] = { '/', 'u', 's', 'r', '/', 'l', 'o', 'c', 'a', 'l', '/', 'p', 'l', 'a', 'n', '9', '/', 'i', 'n', 'c', 'l', 'u', 'd', 'e', 0 }; Runestr file; int i; @@ -443,7 +443,7 @@ includename(Text *t, Rune *r, int n) sprint(buf, "/%s/include", objtype); objdir = bytetorune(buf, &i); objdir = runerealloc(objdir, i+1); - objdir[i] = '\0'; + objdir[i] = '\0'; } w = t->w; @@ -514,6 +514,19 @@ dirname(Text *t, Rune *r, int n) return tmp; } +static int +texthas(Text *t, uint q0, Rune *r) +{ + int i; + + if((int)q0 < 0) + return FALSE; + for(i=0; r[i]; i++) + if(q0+i >= t->file->b.nc || textreadc(t, q0+i) != r[i]) + return FALSE; + return TRUE; +} + int expandfile(Text *t, uint q0, uint q1, Expand *e) { @@ -522,12 +535,14 @@ expandfile(Text *t, uint q0, uint q1, Expand *e) Rune *r, c; Window *w; Runestr rs; + Rune Lhttpcss[] = {'h', 't', 't', 'p', ':', '/', '/', 0}; + Rune Lhttpscss[] = {'h', 't', 't', 'p', 's', ':', '/', '/', 0}; amax = q1; if(q1 == q0){ colon = -1; while(q1<t->file->b.nc && isfilec(c=textreadc(t, q1))){ - if(c == ':'){ + if(c == ':' && !texthas(t, q1-4, Lhttpcss) && !texthas(t, q1-5, Lhttpscss)){ colon = q1; break; } @@ -535,7 +550,7 @@ expandfile(Text *t, uint q0, uint q1, Expand *e) } while(q0>0 && (isfilec(c=textreadc(t, q0-1)) || isaddrc(c) || isregexc(c))){ q0--; - if(colon<0 && c==':') + if(colon<0 && c==':' && !texthas(t, q0-4, Lhttpcss) && !texthas(t, q0-5, Lhttpscss)) colon = q0; } /* @@ -565,8 +580,23 @@ expandfile(Text *t, uint q0, uint q1, Expand *e) if(n == 0) return FALSE; /* see if it's a file name */ - r = runemalloc(n); + r = runemalloc(n+1); bufread(&t->file->b, q0, r, n); + r[n] = 0; + /* is it a URL? look for http:// and https:// prefix */ + if(runestrncmp(r, Lhttpcss, 7) == 0 || runestrncmp(r, Lhttpscss, 8) == 0){ + // Avoid capturing end-of-sentence punctuation. + if(r[n-1] == '.') { + e->q1--; + n--; + } + e->name = r; + e->nname = n; + e->u.at = t; + e->a0 = e->q1; + e->a1 = e->q1; + return TRUE; + } /* first, does it have bad chars? */ nname = -1; for(i=0; i<n; i++){ @@ -728,7 +758,7 @@ openfile(Text *t, Expand *e) /* * Unrooted path in new window. * This can happen if we type a pwd-relative path - * in the topmost tag or the column tags. + * in the topmost tag or the column tags. * Most of the time plumber takes care of these, * but plumber might not be running or might not * be configured to accept plumbed directories. |