Compare commits

...

6 commits

Author SHA1 Message Date
Ori Bernstein
94d9b7a49d cpp: remove stray line from tests 2024-12-22 04:53:12 +00:00
cinap_lenrek
9853ea28c8 /sys/src/9/mkfile: add imx8, lx2k and mt7688 to kernel ARCH list 2024-12-22 03:37:25 +00:00
Ori Bernstein
8b3a70dcd1 git/pull: fix typo 2024-12-22 01:19:50 +00:00
Ori Bernstein
66abd6e50a cpp: implement empty arg handling for function-like macros (thanks rod) 2024-12-22 00:48:14 +00:00
Ori Bernstein
60ea3e6d25 git/pull: only show commit summary after updating branches
this makes human error somewhat harder in noscroll windows.
2024-12-21 22:40:27 +00:00
Ori Bernstein
83fe095033 git/get: support side-band and multi-ack 2024-12-14 17:11:01 +00:00
9 changed files with 187 additions and 85 deletions

View file

@ -1,13 +1,16 @@
ARCH=\ ARCH=\
arm64\ arm64\
bcm\
bcm64\ bcm64\
bcm\
cycv\ cycv\
imx8\
kw\ kw\
lx2k\
mt7688\
#mtx\ #mtx\
omap\ omap\
pc\
pc64\ pc64\
pc\
#ppc\ #ppc\
sgi\ sgi\
teg2\ teg2\

View file

@ -185,7 +185,7 @@ expandrow(Tokenrow *trp, char *flag)
void void
expand(Tokenrow *trp, Nlist *np) expand(Tokenrow *trp, Nlist *np)
{ {
int ntokc, narg, i, hs; int ntokc, narg, nparam, i, hs;
Tokenrow *atr[NARG+1]; Tokenrow *atr[NARG+1];
Tokenrow ntr; Tokenrow ntr;
Token *tp; Token *tp;
@ -202,7 +202,18 @@ expand(Tokenrow *trp, Nlist *np)
/* gatherargs has already pushed trp->tr to the next token */ /* gatherargs has already pushed trp->tr to the next token */
return; return;
} }
if (narg != rowlen(np->ap)) { nparam = rowlen(np->ap);
if(narg == nparam - 1
&& (narg == 0 || (np->flag&ISVARMAC))) {
if(narg == NARG)
error(ERROR, "Too many arguments");
atr[narg] = new(Tokenrow);
maketokenrow(0, atr[narg]);
narg++;
}
if (narg != nparam) {
error(ERROR, "Disagreement in number of macro arguments"); error(ERROR, "Disagreement in number of macro arguments");
trp->tp->hideset = newhideset(trp->tp->hideset, np); trp->tp->hideset = newhideset(trp->tp->hideset, np);
trp->tp += ntokc; trp->tp += ntokc;

View file

@ -2,6 +2,8 @@
-- test nop --
x fooEOF y x fooEOF y
x EOFfoo y x EOFfoo y
x(-1) y x(-1) y
@ -9,26 +11,34 @@ y foo x
x foo y x foo y
X y X y
-- test ncat --
foobar foobar
-- test xcat (no left arg) --
foo ## bar foo ## bar
-- test cat3 --
ablahb ablahb
-- test expand and cat --
33 33
-- test expand and cat 2 --
a bc d a bc d
WUT WUT
-- test varargs --
#line 36 "/sys/src/cmd/cpp/test/edges.in" print("hi","there")
print("hi",)
-- test expanding commas --
@ -48,8 +58,15 @@ WUT
-- test complex expressions --
f(2 * (y+1)) + f(2 * (f(2 * (z[0])))) % f(2 * (0)) + t(1); f(2 * (y+1)) + f(2 * (f(2 * (z[0])))) % f(2 * (0)) + t(1);
f(2 * (2 +(3,4)- 0,1)) | f(2 * (~ 5)) & f(2 * (0,1))^ m(0,1); f(2 * (2 +(3,4)- 0,1)) | f(2 * (~ 5)) & f(2 * (0,1))^ m(0,1);
#line 59 "/sys/src/cmd/cpp/test/edges.in" #line 64 "/sys/src/cmd/cpp/test/edges.in"
#line 66 "/sys/src/cmd/cpp/test/edges.in" -- test empty args --
b
-- test complex expressions with empty args --
int i[] = {1,23,4,5, };
char c[2][6] = {"hello","" };

View file

@ -1,6 +1,8 @@
#define NOP(x) x #define NOP(x) x
#define CAT(a, b) a ## b #define CAT(a, b) a ## b
#define EOF (-1) #define EOF (-1)
-- test nop --
x NOP(CAT(foo, EOF)) y x NOP(CAT(foo, EOF)) y
x NOP(CAT(EOF, foo)) y x NOP(CAT(EOF, foo)) y
x CAT(, EOF) y x CAT(, EOF) y
@ -8,32 +10,34 @@ y CAT(foo,) x
x CAT(,foo) y x CAT(,foo) y
X NOP(CAT(,)) y X NOP(CAT(,)) y
-- test ncat --
#define NCAT(a) foo ## a #define NCAT(a) foo ## a
NCAT(bar) NCAT(bar)
-- test xcat (no left arg) --
#define XCAT(a) ## a #define XCAT(a) ## a
foo XCAT(bar) foo XCAT(bar)
-- test cat3 --
#define CAT3(foo) a##foo##b #define CAT3(foo) a##foo##b
CAT3(blah) CAT3(blah)
-- test expand and cat --
#define BAR 3 #define BAR 3
#define FOO CAT(BAR, 3) #define FOO CAT(BAR, 3)
FOO FOO
-- test expand and cat 2 --
/* Expected: a bc d */ /* Expected: a bc d */
CAT(a b, c d) CAT(a b, c d)
WUT WUT
/* -- test varargs --
* CURRENTLY BROKEN:
* __VA_ARGS__ requires at least one item.
* It should accept an empty list.
#define xprint(a, ...) print(a, __VA_ARGS__) #define xprint(a, ...) print(a, __VA_ARGS__)
xprint("hi", "there") xprint("hi", "there")
xprint("hi") xprint("hi")
*/
-- test expanding commas --
#define C a,b #define C a,b
#define X(a) a #define X(a) a
#define Y X(C) #define Y X(C)
@ -53,13 +57,15 @@ Y
#define q(x) x #define q(x) x
#define r(x,y) x ## y #define r(x,y) x ## y
#define str(x) # x #define str(x) # x
-- test complex expressions --
f(y+1) + f(f(z)) % t(t(g)(0) + t)(1); f(y+1) + f(f(z)) % t(t(g)(0) + t)(1);
g(x+(3,4)-w) | h 5) & m g(x+(3,4)-w) | h 5) & m
(f)^m(m); (f)^m(m);
/*
* CURRENTLY BROKEN: -- test empty args --
* mac() needs at least one argument. #define ZARGS(a) a b a
* It should treat no args as a single empty arg list. ZARGS()
-- test complex expressions with empty args --
p() i[q()] = { q(1), r(2,3), r(4,), r(,5), r(,) }; p() i[q()] = { q(1), r(2,3), r(4,), r(,5), r(,) };
char c[2][6] = { str(hello), str() }; char c[2][6] = { str(hello), str() };
*/

View file

@ -166,16 +166,59 @@ enqueueparent(Objq *q, Object *o)
} }
} }
void
fmtcaps(Conn *c, char *caps, int ncaps)
{
char *p, *e;
p = caps;
e = caps + ncaps;
*p = 0;
if(c->multiack)
p = seprint(p, e, " multi_ack");
if(c->sideband64k)
p = seprint(p, e, " side-band-64k");
else if(c->sideband)
p = seprint(p, e, " side-band");
assert(p != e);
}
int
sbread(Conn *c, char *buf, int nbuf, char **pbuf)
{
int n;
assert(nbuf >= Pktmax);
if(!c->sideband && !c->sideband64k){
*pbuf = buf;
return readn(c->rfd, buf, nbuf);
}else{
*pbuf = buf+1;
while(1){
n = readpkt(c, buf, nbuf);
if(n <= 0)
return n;
else if(buf[0] == 1 && n > 1)
return n - 1;
else if(buf[0] == 3)
fprint(2, "error: %s\n", buf+1);
else if(buf[0] < 1 || buf[0] > 3)
fprint(2, "unknown sideband(%c:%d) data: %s\n", buf[0], buf[0], buf+1);
}
}
}
int int
fetchpack(Conn *c) fetchpack(Conn *c)
{ {
char buf[Pktmax], *sp[3], *ep; char spinner[] = {'|', '/', '-', '\\'};
char *packtmp, *idxtmp, **ref, *caps; char buf[Pktmax], caps[512], *sp[3], *ep;
char *packtmp, *idxtmp, **ref, *rp;
Hash h, *have, *want; Hash h, *have, *want;
int nref, refsz, first, nsent; int nref, refsz, first, nsent;
int i, l, n, req, pfd; int i, j, l, n, spin, req, pfd;
vlong packsz; vlong packsz;
Capset cs;
Objset hadobj; Objset hadobj;
Object *o; Object *o;
Objq haveq; Objq haveq;
@ -195,9 +238,9 @@ fetchpack(Conn *c)
break; break;
if(first && n > strlen(buf)){ if(first && n > strlen(buf)){
parsecaps(buf + strlen(buf) + 1, &cs); parsecaps(buf + strlen(buf) + 1, c);
if(cs.symfrom[0] != 0) if(c->symfrom[0] != 0)
print("symref %s %s\n", cs.symfrom, cs.symto); print("symref %s %s\n", c->symfrom, c->symto);
} }
first = 0; first = 0;
@ -227,18 +270,22 @@ fetchpack(Conn *c)
if(writephase(c) == -1) if(writephase(c) == -1)
sysfatal("write: %r"); sysfatal("write: %r");
req = 0; req = 0;
caps = " multi_ack"; fmtcaps(c, caps, sizeof(caps));
for(i = 0; i < nref; i++){ for(i = 0; i < nref; i++){
if(hasheq(&have[i], &want[i])) if(hasheq(&have[i], &want[i]))
continue; continue;
for(j = 0; j < i; j++)
if(hasheq(&want[i], &want[j]))
goto Next;
if((o = readobject(want[i])) != nil){ if((o = readobject(want[i])) != nil){
unref(o); unref(o);
continue; continue;
} }
if(fmtpkt(c, "want %H%s\n", want[i], caps) == -1) if(fmtpkt(c, "want %H%s\n", want[i], caps) == -1)
sysfatal("could not send want for %H", want[i]); sysfatal("could not send want for %H", want[i]);
caps = ""; caps[0] = 0;
req = 1; req = 1;
Next: continue;
} }
flushpkt(c); flushpkt(c);
@ -261,6 +308,7 @@ fetchpack(Conn *c)
enqueueparent(&haveq, o); enqueueparent(&haveq, o);
osadd(&hadobj, o); osadd(&hadobj, o);
unref(o); unref(o);
nsent++;
} }
/* /*
* While we could short circuit this and check if upstream has * While we could short circuit this and check if upstream has
@ -274,7 +322,7 @@ fetchpack(Conn *c)
if(oshas(&hadobj, e.o->hash)) if(oshas(&hadobj, e.o->hash))
continue; continue;
if((o = readobject(e.o->hash)) == nil) if((o = readobject(e.o->hash)) == nil)
sysfatal("missing object we should have: %H", have[i]); sysfatal("missing object we should have: %H", e.o->hash);
if(fmtpkt(c, "have %H", o->hash) == -1) if(fmtpkt(c, "have %H", o->hash) == -1)
sysfatal("write: %r"); sysfatal("write: %r");
enqueueparent(&haveq, o); enqueueparent(&haveq, o);
@ -292,9 +340,6 @@ fetchpack(Conn *c)
goto showrefs; goto showrefs;
if(readphase(c) == -1) if(readphase(c) == -1)
sysfatal("read: %r"); sysfatal("read: %r");
if((n = readpkt(c, buf, sizeof(buf))) == -1)
sysfatal("read: %r");
buf[n] = 0;
if((packtmp = smprint(".git/objects/pack/fetch.%d.pack", getpid())) == nil) if((packtmp = smprint(".git/objects/pack/fetch.%d.pack", getpid())) == nil)
sysfatal("smprint: %r"); sysfatal("smprint: %r");
@ -305,38 +350,56 @@ fetchpack(Conn *c)
if((pfd = create(packtmp, ORDWR, 0664)) == -1) if((pfd = create(packtmp, ORDWR, 0664)) == -1)
sysfatal("could not create %s: %r", packtmp); sysfatal("could not create %s: %r", packtmp);
fprint(2, "fetching...\n"); fprint(2, "fetching... ");
/* packsz = 0;
* Work around torvalds git bug: we get duplicate have lines if(c->multiack){
* somtimes, even though the protocol is supposed to start the for(i = 0; i < nsent; i++){
* pack file immediately. if(readpkt(c, buf, sizeof(buf)) == -1)
* sysfatal("read: %r");
* Skip ahead until we read 'PACK' off the wire if(strncmp(buf, "NAK\n", 4) == 0)
*/ break;
while(1){ if(strncmp(buf, "ACK ", 4) != 0)
if(readn(c->rfd, buf, 4) != 4) sysfatal("bad response: '%s'", buf);
sysfatal("fetch packfile: short read"); }
buf[4] = 0; }
if(strncmp(buf, "PACK", 4) == 0) if(readpkt(c, buf, sizeof(buf)) == -1)
break; sysfatal("read: %r");
l = strtol(buf, &ep, 16); if(!c->sideband && !c->sideband64k && !c->multiack){
if(ep != buf + 4) /*
sysfatal("fetch packfile: junk pktline"); * Work around torvalds git bug: we get duplicate have lines
if(readn(c->rfd, buf, l-4) != l-4) * somtimes, even though the protocol is supposed to start the
sysfatal("fetch packfile: short read"); * pack file immediately.
*
* Skip ahead until we read 'PACK' off the wire
*/
while(1){
if(readn(c->rfd, buf, 4) != 4)
sysfatal("fetch packfile: short read");
if(strncmp(buf, "PACK", 4) == 0)
break;
buf[4] = 0;
l = strtol(buf, &ep, 16);
if(ep != buf + 4)
sysfatal("fetch packfile: junk pktline");
if(readn(c->rfd, buf, l-4) != l-4)
sysfatal("fetch packfile: short read");
}
if(write(pfd, "PACK", 4) != 4)
sysfatal("write pack header: %r");
packsz = 4;
} }
if(write(pfd, "PACK", 4) != 4) spin = 0;
sysfatal("write pack header: %r");
packsz = 4;
while(1){ while(1){
n = read(c->rfd, buf, sizeof buf); n = sbread(c, buf, sizeof buf, &rp);
if(n == 0) if(n == 0)
break; break;
if(n == -1 || write(pfd, buf, n) != n) if(n == -1 || write(pfd, rp, n) != n)
sysfatal("fetch packfile: %r"); sysfatal("fetch packfile: %r");
if(interactive && spin++ % 100 == 0)
fprint(2, "\b%c", spinner[spin/100 % nelem(spinner)]);
packsz += n; packsz += n;
} }
fprint(2, "\n");
closeconn(c); closeconn(c);
if(seek(pfd, 0, 0) == -1) if(seek(pfd, 0, 0) == -1)
fail(packtmp, idxtmp, "packfile seek: %r"); fail(packtmp, idxtmp, "packfile seek: %r");

View file

@ -4,7 +4,6 @@
#include <flate.h> #include <flate.h>
#include <regexp.h> #include <regexp.h>
typedef struct Capset Capset;
typedef struct Conn Conn; typedef struct Conn Conn;
typedef struct Hash Hash; typedef struct Hash Hash;
typedef struct Delta Delta; typedef struct Delta Delta;
@ -82,19 +81,19 @@ struct Hash {
uchar h[20]; uchar h[20];
}; };
struct Capset {
char symfrom[256];
char symto[256];
int sideband;
int sideband64k;
int report;
};
struct Conn { struct Conn {
int type; int type;
int rfd; int rfd;
int wfd; int wfd;
/* capabilities */
char symfrom[256];
char symto[256];
char multiack;
char sideband;
char sideband64k;
char report;
/* only used by http */ /* only used by http */
int cfd; int cfd;
char *url; /* note, first GET uses a different url */ char *url; /* note, first GET uses a different url */
@ -338,7 +337,7 @@ int gitconnect(Conn *, char *, char *);
int readphase(Conn *); int readphase(Conn *);
int writephase(Conn *); int writephase(Conn *);
void closeconn(Conn *); void closeconn(Conn *);
void parsecaps(char *, Capset *); void parsecaps(char *, Conn *);
/* queues */ /* queues */
void qinit(Objq*); void qinit(Objq*);

View file

@ -27,27 +27,28 @@ matchcap(char *s, char *cap, int full)
} }
void void
parsecaps(char *caps, Capset *cs) parsecaps(char *caps, Conn *c)
{ {
char *p, *n, *c, *t; char *p, *n, *s, *t;
memset(cs, 0, sizeof(*cs));
for(p = caps; p != nil; p = n){ for(p = caps; p != nil; p = n){
n = strchr(p, ' '); n = strchr(p, ' ');
if(n != nil) if(n != nil)
*n++ = 0; *n++ = 0;
if(matchcap(p, "report-status", 1) != nil) if(matchcap(p, "report-status", 1) != nil)
cs->report = 1; c->report = 1;
if(matchcap(p, "multi_ack", 1) != nil)
c->multiack = 1;
else if(matchcap(p, "side-band", 1) != nil) else if(matchcap(p, "side-band", 1) != nil)
cs->sideband = 1; c->sideband = 1;
else if(matchcap(p, "side-band-64k", 1) != nil) else if(matchcap(p, "side-band-64k", 1) != nil)
cs->sideband64k = 1; c->sideband64k = 1;
else if((c = matchcap(p, "symref=", 0)) != nil){ else if((s = matchcap(p, "symref=", 0)) != nil){
if((t = strchr(c, ':')) == nil) if((t = strchr(s, ':')) == nil)
continue; continue;
*t++ = '\0'; *t++ = '\0';
snprint(cs->symfrom, sizeof(cs->symfrom), c); snprint(c->symfrom, sizeof(c->symfrom), s);
snprint(cs->symto, sizeof(cs->symto), t); snprint(c->symto, sizeof(c->symto), t);
} }
} }
} }
@ -108,7 +109,7 @@ readpkt(Conn *c, char *buf, int nbuf)
sysfatal("pktline: bad length '%s'", len); sysfatal("pktline: bad length '%s'", len);
n -= 4; n -= 4;
if(n >= nbuf) if(n >= nbuf)
sysfatal("pktline: undersize buffer"); abort();//sysfatal("pktline: undersize buffer");
if(readn(c->rfd, buf, n) != n) if(readn(c->rfd, buf, n) != n)
return -1; return -1;
if(n > 4 && strncmp(buf, "ERR ", 4) == 0){ if(n > 4 && strncmp(buf, "ERR ", 4) == 0){
@ -468,7 +469,6 @@ static int
localrepo(char *uri, char *path, int npath) localrepo(char *uri, char *path, int npath)
{ {
int fd; int fd;
snprint(path, npath, "%s/.git/../", uri); snprint(path, npath, "%s/.git/../", uri);
fd = open(path, OREAD); fd = open(path, OREAD);
if(fd < 0) if(fd < 0)

View file

@ -63,10 +63,15 @@ if(! ~ `{git/query HEAD $remote @} `{git/query HEAD}){
} }
exit diverged exit diverged
} }
oldcommit=`{git/query $local}
newcommit=`{git/query $remote}
echo $remote':' $oldcommit '=>' $newcommit
git/branch -mnb $remote $local
# The remote is directly ahead of the local, and we have # The remote is directly ahead of the local, and we have
# no local commits that need merging. # no local commits that need merging.
if(~ $#quiet 0) if(~ $#quiet 0)
git/log -s -e $local'..'$remote git/log -s -e $oldcommit'..'$newcommit
echo $remote':' `{git/query $local} '=>' `{git/query $remote}
git/branch -mnb $remote $local
exit '' exit ''

View file

@ -91,11 +91,9 @@ sendpack(Conn *c)
Hash h, *theirs, *ours; Hash h, *theirs, *ours;
Object *a, *b, *p, *o; Object *a, *b, *p, *o;
char **refs; char **refs;
Capset cs;
Map *map, *m; Map *map, *m;
first = 1; first = 1;
memset(&cs, 0, sizeof(Capset));
nours = readours(&ours, &refs); nours = readours(&ours, &refs);
theirs = nil; theirs = nil;
ntheirs = 0; ntheirs = 0;
@ -113,7 +111,7 @@ sendpack(Conn *c)
if(n == 0) if(n == 0)
break; break;
if(first && n > strlen(buf)) if(first && n > strlen(buf))
parsecaps(buf + strlen(buf) + 1, &cs); parsecaps(buf + strlen(buf) + 1, c);
first = 0; first = 0;
if(getfields(buf, sp, nelem(sp), 1, " \t\r\n") != 2) if(getfields(buf, sp, nelem(sp), 1, " \t\r\n") != 2)
@ -179,7 +177,7 @@ sendpack(Conn *c)
* Github doesn't advertise any capabilities, so we can't check * Github doesn't advertise any capabilities, so we can't check
* for compatibility. We just need to add it blindly. * for compatibility. We just need to add it blindly.
*/ */
if(i == 0 && cs.report){ if(i == 0 && c->report){
buf[n++] = '\0'; buf[n++] = '\0';
n += snprint(buf + n, sizeof(buf) - n, " report-status"); n += snprint(buf + n, sizeof(buf) - n, " report-status");
} }
@ -195,7 +193,7 @@ sendpack(Conn *c)
if(writepack(c->wfd, ours, nours, theirs, ntheirs, &h) == -1) if(writepack(c->wfd, ours, nours, theirs, ntheirs, &h) == -1)
return -1; return -1;
if(!cs.report) if(!c->report)
return 0; return 0;
if(readphase(c) == -1) if(readphase(c) == -1)