OK, turing.

<- leave blank

Tue Jun 6 16:39:04 EDT 2023

Hydra Lorem ipsum
Hydra Lorem ipsum
Hydra Lorem ipsum
Hydra Lorem ipsum

Tue Jun 6 06:16:10 EDT 2023
'';

Mon Jun 5 19:22:47 EDT 2023
(defun broadcast-live-peers ()
  (broadcast (loop with t0 = (get-universal-time)
		   for s in stations
		   when (< (- t0 (last-packet-timestamp s)) 30)
		     collect (operator s) into r
		   finally (return (format nil "live peers: ~{~a~^, ~}" (sort r
		   #'string-lessp))))))


Mon Jun 5 19:05:25 EDT 2023
diff 4914b987d711b076542b72c1717fb59c6ebebef9 uncommitted
--- a//rc/bin/termrc
+++ b//rc/bin/termrc
@@ -93,4 +93,9 @@
 if(test -f /dev/apm)
	aux/apm

+if(~ $terminal *reform*){
+ reform/pm
+ reform/audio
+}
+
 dontkill
 '^(ipconfig|factotum|mntgen|venti|hjfs|kfs|cfs|cwfs.*|9660srv|dossrv|paqfs|cs|dns|listen|reboot|usbd|kb|disk|ether|wpa)$'


Mon Jun 5 17:38:06 EDT 2023
To: tuhs@tuhs.org
Date: Mon, 5 Jun 2023 15:30:23 -0400 (EDT)
From: norman@oclsc.org (Norman Wilson)
Message-ID-Hash: MYXMVXXPGRGR5NKFTB54FFDHIDJBZFAT
Subject: [TUHS] Re: CB-UNIX dsw(1l) Page from PDP-7?
Archived-At:
<https://www.tuhs.org/mailman3/hyperkitty/list/tuhs@tuhs.org/message/MYXMVXXPGRGR5NKFTB54FFDHIDJBZFAT/>

Rather an aside, but the alt.sysadmin.recovery message referenced
in https://www.tuhs.org/pipermail/tuhs/1999-November/001203.html
chimes interesting chords for me.

If you care only about technical stuff, you should skip to
your next e-mail message now.

On one hand, the doubly-embedded net.unix-wizards message
from Dennis, dated 1984-12-08, containing the original dsw.s:
that was posted a few months after I joined Bell Labs, and
may even have been partly my fault.  1984 was the nominal
15th anniversary of UNIX; as a member of the steering committee
of the recently-formed UNIX* Special Interest Group in US DECUS,
I convinced Dennis to attend the Fall 1984 Symposium, in Anaheim
in early December, as part of a celebration.  As another part, I
made copies of the V1-V7 manuals in the UNIX Room and had them
shipped out so people could leaf through the history.  I think
Dennis dug out the PDP-7 source-code books as a contribution to
that effort; I am all but certain we brought copies of those too.

Of course I had the copies returned not to the Labs but to my
home address.  I still have them, now on a shelf in my home office.
A good friend offered to take care of shipping them back to New
Jersey, of course making her own copies in return.

I also recall that the conference hotel happened to give me
room 127.  I offered to swap with Dennis, since he deserved
that number more than I did (the extra digit had already been
prepended before I joined) but he cheerfully declined.

On the other hand--not as historic except to me--the author
of the singly-embedded 1999-11-23 alt.sysadmin.recovery message
is now (and has for some years been) a co-worker and a good
friend.

So this single 1999 TUHS posting touches points near both
the beginning and the end (so far) of my career, and two
different groups of smart people who are fun to work with.

Norman Wilson
Toronto ON




Sun Jun 4 13:40:20 EDT 2023
diff 25319382697878e01b9949afb33fcc6f4c4e6e1d uncommitted
--- a/sys/src/cmd/git/serve.c
+++ b/sys/src/cmd/git/serve.c
@@ -7,12 +7,28 @@

 char *pathpfx = nil;
 int allowwrite;
+int report;

 int
+parsecaps(char *caps)
+{
+ char *p, *n;
+
+ for(p = caps; p != nil; p = n){
+ if((n = strchr(p, ' ')) != nil)
+ *n++ = 0;
+ if(strcmp(p, "report-status") == 0)
+ report = 1;
+ }
+ return 0;
+}
+
+int
 showrefs(Conn *c)
 {
- int i, ret, nrefs;
+ int i, sentcap, ret, nrefs;
	Hash head, *refs;
+ char *p, *e, pkt[Pktmax];
	char **names;

	ret = -1;
@@ -19,9 +35,17 @@
	nrefs = 0;
	refs = nil;
	names = nil;
- if(resolveref(&head, "HEAD") != -1)
- if(fmtpkt(c, "%H HEAD\n", head) == -1)
+ sentcap = 0;
+ if(resolveref(&head, "HEAD") != -1){
+ p = pkt;
+ e = pkt+sizeof(pkt);
+ p = seprint(p, e, "%H HEAD\n", head);
+ *p++ = 0;
+ p = seprint(p, e, "report-status");
+ sentcap = 1;
+ if(writepkt(c, pkt, p-pkt) == -1)
			goto error;
+ }

	if((nrefs = listrefs(&refs, &names)) == -1)
		sysfatal("listrefs: %r");
@@ -28,7 +52,15 @@
	for(i = 0; i < nrefs; i++){
		if(strncmp(names[i], "heads/", strlen("heads/")) != 0)
			continue;
- if(fmtpkt(c, "%H refs/%s\n", refs[i], names[i]) == -1)
+ p = pkt;
+ e = pkt+sizeof(pkt);
+ p = seprint(p, e, "%H refs/%s\n", refs[i], names[i]);
+ if(!sentcap){
+ *p++ = 0;
+ p = seprint(p, e, "report-status");
+ sentcap = 1;
+ }
+ if(writepkt(c, pkt, p-pkt) == -1)
			goto error;
	}
	if(flushpkt(c) == -1)
@@ -45,8 +77,8 @@
 int
 servnegotiate(Conn *c, Hash **head, int *nhead, Hash **tail, int *ntail)
 {
- char pkt[Pktmax];
- int n, acked;
+ char *sp[3], pkt[Pktmax];
+ int n, nsp, acked;
	Object *o;
	Hash h;

@@ -62,14 +94,22 @@
			goto error;
		if(n == 0)
			break;
- if(strncmp(pkt, "want ", 5) != 0){
+ if((nsp = getfields(pkt, sp, nelem(sp), 1, " \t")) < 2){
+ werrstr("protocol garble %s", pkt);
+ goto error;
+ }
+ if(strcmp(sp[0], "want") != 0){
			werrstr(" protocol garble %s", pkt);
			goto error;
		}
- if(hparse(&h, &pkt[5]) == -1){
+ if(hparse(&h, sp[1]) == -1){
			werrstr(" garbled want");
			goto error;
		}
+ if(nsp > 2 && parsecaps(sp[2]) == -1){
+ werrstr("garbled caps %s", sp[2]);
+ goto error;
+ }
		if((o = readobject(h)) == nil){
			werrstr("requested nonexistent object");
			goto error;
@@ -151,7 +191,7 @@
 {
	char pkt[Pktmax], *sp[4];
	Hash old, new;
- int n, i;
+ int l, n, i;

	if(showrefs(c) == -1)
		return -1;
@@ -164,6 +204,11 @@
			goto error;
		if(n == 0)
			break;
+ l = strlen(pkt);
+ if(n > l+1 && parsecaps(pkt+l+1) == -1){
+ fmtpkt(c, "ERR protocol garble %s\n", pkt);
+ goto error;
+ }
		if(getfields(pkt, sp, nelem(sp), 1, " \t\n\r") != 3){
			fmtpkt(c, "ERR protocol garble %s\n", pkt);
			goto error;
@@ -314,21 +359,26 @@
		packsz += n;
	}
	if(checkhash(pfd, packsz, &h) == -1){
- dprint(1, "hash mismatch\n");
+ werrstr("hash mismatch\n");
		goto error1;
	}
	if(indexpack(packtmp, idxtmp, h) == -1){
- dprint(1, "indexing failed: %r\n");
+ werrstr("indexing failed: %r\n");
		goto error1;
	}
	if(rename(packtmp, idxtmp, h) == -1){
- dprint(1, "rename failed: %r\n");
+ werrstr("rename failed: %r\n");
		goto error2;
	}
+ if(report)
+ fmtpkt(c, "unpack ok");
	return 0;

 error2: remove(idxtmp);
 error1: remove(packtmp);
+ dprint(1, "update pack: %r");
+ if(report)
+ fmtpkt(c, "unpack %r");
	return -1;
 }

@@ -348,12 +398,13 @@
 int
 updaterefs(Conn *c, Hash *cur, Hash *upd, char **ref, int nupd)
 {
- char refpath[512], buf[128];
- int i, newidx, hadref, fd, ret, lockfd;
+ char refpath[512];
+ int i, j, newidx, hadref, fd, ret, lockfd;
	vlong newtm;
	Object *o;
	Hash h;

+ i = 0;
	ret = -1;
	hadref = 0;
	newidx = -1;
@@ -364,20 +415,20 @@
	 */
	newtm = -23811206400;
	if((lockfd = lockrepo()) == -1){
- snprint(buf, sizeof(buf), "repo locked\n");
- return -1;
+ werrstr("repo locked\n");
+ goto out;
	}
	for(i = 0; i < nupd; i++){
		if(resolveref(&h, ref[i]) == 0){
			hadref = 1;
			if(!hasheq(&h, &cur[i])){
- snprint(buf, sizeof(buf), "old ref changed: %s", ref[i]);
- goto error;
+ werrstr("old ref changed: %s", ref[i]);
+ goto out;
			}
		}
		if(snprint(refpath, sizeof(refpath), ".git/%s", ref[i]) ==
		sizeof(refpath)){
- snprint(buf, sizeof(buf), "ref path too long: %s", ref[i]);
- goto error;
+ werrstr("ref path too long: %s", ref[i]);
+ goto out;
		}
		if(hasheq(&upd[i], &Zhash)){
			remove(refpath);
@@ -384,12 +435,12 @@
			continue;
		}
		if((o = readobject(upd[i])) == nil){
- snprint(buf, sizeof(buf), "update to nonexistent hash %H", upd[i]);
- goto error;
+ werrstr("update to nonexistent hash %H", upd[i]);
+ goto out;
		}
		if(o->type != GCommit){
- snprint(buf, sizeof(buf), "not commit: %H", upd[i]);
- goto error;
+ werrstr("not commit: %H", upd[i]);
+ goto out;
		}
		if(o->commit->mtime > newtm){
			newtm = o->commit->mtime;
@@ -397,13 +448,13 @@
		}
		unref(o);
		if((fd = create(refpath, OWRITE|OTRUNC, 0644)) == -1){
- snprint(buf, sizeof(buf), "open ref: %r");
- goto error;
+ werrstr("open ref: %r");
+ goto out;
		}
		if(fprint(fd, "%H", upd[i]) == -1){
- snprint(buf, sizeof(buf), "upate ref: %r");
+ werrstr("upate ref: %r");
			close(fd);
- goto error;
+ goto out;
		}
		close(fd);
	}
@@ -420,22 +471,30 @@
	 * use.  This should make us pick a useful default in
	 * those cases, instead of silently failing.
	 */
+ i = 0;
	if(resolveref(&h, "HEAD") == -1 && hadref == 0 && newidx != -1){
		if((fd = create(".git/HEAD", OWRITE|OTRUNC, 0644)) == -1){
- snprint(buf, sizeof(buf), "open HEAD: %r");
- goto error;
+ werrstr("open HEAD: %r");
+ goto out;
		}
- if(fprint(fd, "ref: %s", ref[0]) == -1){
- snprint(buf, sizeof(buf), "write HEAD ref: %r");
- goto error;
+ if(fprint(fd, "ref: %s", ref[i]) == -1){
+ werrstr("write HEAD ref: %r");
+ goto out;
		}
		close(fd);
	}
	ret = 0;
-error:
- fmtpkt(c, "ERR %s", buf);
- close(lockfd);
- werrstr(buf);
+out:
+ if(report){
+ for(j = 0; j < nupd; j++){
+ if(i != j || ret == 0)
+ fmtpkt(c, "ok %s", ref[i]);
+ else
+ fmtpkt(c, "ng %s %r\n", ref[i]);
+ }
+ }
+ if(lockfd != -1)
+ close(lockfd);
	return ret;
 }



Sun Jun 4 13:06:04 EDT 2023
diff 25319382697878e01b9949afb33fcc6f4c4e6e1d uncommitted
--- a/sys/src/cmd/git/serve.c
+++ b/sys/src/cmd/git/serve.c
@@ -7,12 +7,28 @@

 char *pathpfx = nil;
 int allowwrite;
+int report;

 int
+parsecaps(char *caps)
+{
+ char *p, *n;
+
+ for(p = caps; p != nil; p = n){
+ if((n = strchr(p, ' ')) != nil)
+ *n++ = 0;
+ if(strcmp(p, "report-status") == 0)
+ report = 1;
+ }
+ return 0;
+}
+
+int
 showrefs(Conn *c)
 {
	int i, ret, nrefs;
	Hash head, *refs;
+ char *p, *e, pkt[Pktmax];
	char **names;

	ret = -1;
@@ -28,7 +44,14 @@
	for(i = 0; i < nrefs; i++){
		if(strncmp(names[i], "heads/", strlen("heads/")) != 0)
			continue;
- if(fmtpkt(c, "%H refs/%s\n", refs[i], names[i]) == -1)
+ p = pkt;
+ e = pkt+sizeof(pkt);
+ p = seprint(p, e, "%H refs/%s\n", refs[i], names[i]);
+ if(i == 0){
+ *p++ = 0;
+ p = seprint(p, e, "report-status");
+ }
+ if(writepkt(c, pkt, p-pkt) == -1)
			goto error;
	}
	if(flushpkt(c) == -1)
@@ -45,8 +68,8 @@
 int
 servnegotiate(Conn *c, Hash **head, int *nhead, Hash **tail, int *ntail)
 {
- char pkt[Pktmax];
- int n, acked;
+ char *sp[3], pkt[Pktmax];
+ int n, nsp, acked;
	Object *o;
	Hash h;

@@ -62,14 +85,22 @@
			goto error;
		if(n == 0)
			break;
- if(strncmp(pkt, "want ", 5) != 0){
+ if((nsp = getfields(pkt, sp, nelem(sp), 1, " \t")) < 2){
+ werrstr("protocol garble %s", pkt);
+ goto error;
+ }
+ if(strcmp(sp[0], "want") != 0){
			werrstr(" protocol garble %s", pkt);
			goto error;
		}
- if(hparse(&h, &pkt[5]) == -1){
+ if(hparse(&h, sp[1]) == -1){
			werrstr(" garbled want");
			goto error;
		}
+ if(nsp > 2 && parsecaps(sp[2]) == -1){
+ werrstr("garbled caps %s", sp[2]);
+ goto error;
+ }
		if((o = readobject(h)) == nil){
			werrstr("requested nonexistent object");
			goto error;
@@ -151,7 +182,7 @@
 {
	char pkt[Pktmax], *sp[4];
	Hash old, new;
- int n, i;
+ int l, n, i;

	if(showrefs(c) == -1)
		return -1;
@@ -164,6 +195,11 @@
			goto error;
		if(n == 0)
			break;
+ l = strlen(pkt);
+ if(n > l+1 && parsecaps(pkt+l+1) == -1){
+ fmtpkt(c, "ERR protocol garble %s\n", pkt);
+ goto error;
+ }
		if(getfields(pkt, sp, nelem(sp), 1, " \t\n\r") != 3){
			fmtpkt(c, "ERR protocol garble %s\n", pkt);
			goto error;
@@ -314,21 +350,26 @@
		packsz += n;
	}
	if(checkhash(pfd, packsz, &h) == -1){
- dprint(1, "hash mismatch\n");
+ werrstr("hash mismatch\n");
		goto error1;
	}
	if(indexpack(packtmp, idxtmp, h) == -1){
- dprint(1, "indexing failed: %r\n");
+ werrstr("indexing failed: %r\n");
		goto error1;
	}
	if(rename(packtmp, idxtmp, h) == -1){
- dprint(1, "rename failed: %r\n");
+ werrstr("rename failed: %r\n");
		goto error2;
	}
+ if(report)
+ fmtpkt(c, "unpack ok");
	return 0;

 error2: remove(idxtmp);
 error1: remove(packtmp);
+ dprint(1, "update pack: %r");
+ if(report)
+ fmtpkt(c, "unpack %r");
	return -1;
 }

@@ -348,12 +389,13 @@
 int
 updaterefs(Conn *c, Hash *cur, Hash *upd, char **ref, int nupd)
 {
- char refpath[512], buf[128];
- int i, newidx, hadref, fd, ret, lockfd;
+ char refpath[512];
+ int i, j, newidx, hadref, fd, ret, lockfd;
	vlong newtm;
	Object *o;
	Hash h;

+ i = 0;
	ret = -1;
	hadref = 0;
	newidx = -1;
@@ -364,20 +406,20 @@
	 */
	newtm = -23811206400;
	if((lockfd = lockrepo()) == -1){
- snprint(buf, sizeof(buf), "repo locked\n");
- return -1;
+ werrstr("repo locked\n");
+ goto out;
	}
	for(i = 0; i < nupd; i++){
		if(resolveref(&h, ref[i]) == 0){
			hadref = 1;
			if(!hasheq(&h, &cur[i])){
- snprint(buf, sizeof(buf), "old ref changed: %s", ref[i]);
- goto error;
+ werrstr("old ref changed: %s", ref[i]);
+ goto out;
			}
		}
		if(snprint(refpath, sizeof(refpath), ".git/%s", ref[i]) ==
		sizeof(refpath)){
- snprint(buf, sizeof(buf), "ref path too long: %s", ref[i]);
- goto error;
+ werrstr("ref path too long: %s", ref[i]);
+ goto out;
		}
		if(hasheq(&upd[i], &Zhash)){
			remove(refpath);
@@ -384,12 +426,12 @@
			continue;
		}
		if((o = readobject(upd[i])) == nil){
- snprint(buf, sizeof(buf), "update to nonexistent hash %H", upd[i]);
- goto error;
+ werrstr("update to nonexistent hash %H", upd[i]);
+ goto out;
		}
		if(o->type != GCommit){
- snprint(buf, sizeof(buf), "not commit: %H", upd[i]);
- goto error;
+ werrstr("not commit: %H", upd[i]);
+ goto out;
		}
		if(o->commit->mtime > newtm){
			newtm = o->commit->mtime;
@@ -397,13 +439,13 @@
		}
		unref(o);
		if((fd = create(refpath, OWRITE|OTRUNC, 0644)) == -1){
- snprint(buf, sizeof(buf), "open ref: %r");
- goto error;
+ werrstr("open ref: %r");
+ goto out;
		}
		if(fprint(fd, "%H", upd[i]) == -1){
- snprint(buf, sizeof(buf), "upate ref: %r");
+ werrstr("upate ref: %r");
			close(fd);
- goto error;
+ goto out;
		}
		close(fd);
	}
@@ -420,22 +462,30 @@
	 * use.  This should make us pick a useful default in
	 * those cases, instead of silently failing.
	 */
+ i = 0;
	if(resolveref(&h, "HEAD") == -1 && hadref == 0 && newidx != -1){
		if((fd = create(".git/HEAD", OWRITE|OTRUNC, 0644)) == -1){
- snprint(buf, sizeof(buf), "open HEAD: %r");
- goto error;
+ werrstr("open HEAD: %r");
+ goto out;
		}
- if(fprint(fd, "ref: %s", ref[0]) == -1){
- snprint(buf, sizeof(buf), "write HEAD ref: %r");
- goto error;
+ if(fprint(fd, "ref: %s", ref[i]) == -1){
+ werrstr("write HEAD ref: %r");
+ goto out;
		}
		close(fd);
	}
	ret = 0;
-error:
- fmtpkt(c, "ERR %s", buf);
- close(lockfd);
- werrstr(buf);
+out:
+ if(lockfd != -1)
+ close(lockfd);
+ if(!report)
+ return ret;
+ for(j = 0; j < nupd; j++){
+ if(i != j || ret == 0)
+ fmtpkt(c, "ok %s", ref[i]);
+ else
+ fmtpkt(c, "ng %s %r\n", ref[i]);
+ }
	return ret;
 }



Sun Jun 4 13:05:52 EDT 2023
diff 25319382697878e01b9949afb33fcc6f4c4e6e1d uncommitted
--- a/sys/src/cmd/git/serve.c
+++ b/sys/src/cmd/git/serve.c
@@ -7,12 +7,28 @@

 char *pathpfx = nil;
 int allowwrite;
+int report;

 int
+parsecaps(char *caps)
+{
+ char *p, *n;
+
+ for(p = caps; p != nil; p = n){
+ if((n = strchr(p, ' ')) != nil)
+ *n++ = 0;
+ if(strcmp(p, "report-status") == 0)
+ report = 1;
+ }
+ return 0;
+}
+
+int
 showrefs(Conn *c)
 {
	int i, ret, nrefs;
	Hash head, *refs;
+ char *p, *e, pkt[Pktmax];
	char **names;

	ret = -1;
@@ -28,7 +44,14 @@
	for(i = 0; i < nrefs; i++){
		if(strncmp(names[i], "heads/", strlen("heads/")) != 0)
			continue;
- if(fmtpkt(c, "%H refs/%s\n", refs[i], names[i]) == -1)
+ p = pkt;
+ e = pkt+sizeof(pkt);
+ p = seprint(p, e, "%H refs/%s\n", refs[i], names[i]);
+ if(i == 0){
+ *p++ = 0;
+ p = seprint(p, e, "report-status");
+ }
+ if(writepkt(c, pkt, p-pkt) == -1)
			goto error;
	}
	if(flushpkt(c) == -1)
@@ -45,8 +68,8 @@
 int
 servnegotiate(Conn *c, Hash **head, int *nhead, Hash **tail, int *ntail)
 {
- char pkt[Pktmax];
- int n, acked;
+ char *sp[3], pkt[Pktmax];
+ int n, nsp, acked;
	Object *o;
	Hash h;

@@ -62,14 +85,22 @@
			goto error;
		if(n == 0)
			break;
- if(strncmp(pkt, "want ", 5) != 0){
+ if((nsp = getfields(pkt, sp, nelem(sp), 1, " \t")) < 2){
+ werrstr("protocol garble %s", pkt);
+ goto error;
+ }
+ if(strcmp(sp[0], "want") != 0){
			werrstr(" protocol garble %s", pkt);
			goto error;
		}
- if(hparse(&h, &pkt[5]) == -1){
+ if(hparse(&h, sp[1]) == -1){
			werrstr(" garbled want");
			goto error;
		}
+ if(nsp > 2 && parsecaps(sp[2]) == -1){
+ werrstr("garbled caps %s", sp[2]);
+ goto error;
+ }
		if((o = readobject(h)) == nil){
			werrstr("requested nonexistent object");
			goto error;
@@ -151,7 +182,7 @@
 {
	char pkt[Pktmax], *sp[4];
	Hash old, new;
- int n, i;
+ int l, n, i;

	if(showrefs(c) == -1)
		return -1;
@@ -164,6 +195,11 @@
			goto error;
		if(n == 0)
			break;
+ l = strlen(pkt);
+ if(n > l+1 && parsecaps(pkt+l+1) == -1){
+ fmtpkt(c, "ERR protocol garble %s\n", pkt);
+ goto error;
+ }
		if(getfields(pkt, sp, nelem(sp), 1, " \t\n\r") != 3){
			fmtpkt(c, "ERR protocol garble %s\n", pkt);
			goto error;
@@ -314,21 +350,26 @@
		packsz += n;
	}
	if(checkhash(pfd, packsz, &h) == -1){
- dprint(1, "hash mismatch\n");
+ werrstr("hash mismatch\n");
		goto error1;
	}
	if(indexpack(packtmp, idxtmp, h) == -1){
- dprint(1, "indexing failed: %r\n");
+ werrstr("indexing failed: %r\n");
		goto error1;
	}
	if(rename(packtmp, idxtmp, h) == -1){
- dprint(1, "rename failed: %r\n");
+ werrstr("rename failed: %r\n");
		goto error2;
	}
+ if(report)
+ fmtpkt(c, "unpack ok");
	return 0;

 error2: remove(idxtmp);
 error1: remove(packtmp);
+ dprint(1, "update pack: %r");
+ if(report)
+ fmtpkt(c, "unpack %r");
	return -1;
 }

@@ -348,12 +389,13 @@
 int
 updaterefs(Conn *c, Hash *cur, Hash *upd, char **ref, int nupd)
 {
- char refpath[512], buf[128];
- int i, newidx, hadref, fd, ret, lockfd;
+ char refpath[512];//, buf[128];
+ int i, j, newidx, hadref, fd, ret, lockfd;
	vlong newtm;
	Object *o;
	Hash h;

+ i = 0;
	ret = -1;
	hadref = 0;
	newidx = -1;
@@ -364,20 +406,20 @@
	 */
	newtm = -23811206400;
	if((lockfd = lockrepo()) == -1){
- snprint(buf, sizeof(buf), "repo locked\n");
- return -1;
+ werrstr("repo locked\n");
+ goto out;
	}
	for(i = 0; i < nupd; i++){
		if(resolveref(&h, ref[i]) == 0){
			hadref = 1;
			if(!hasheq(&h, &cur[i])){
- snprint(buf, sizeof(buf), "old ref changed: %s", ref[i]);
- goto error;
+ werrstr("old ref changed: %s", ref[i]);
+ goto out;
			}
		}
		if(snprint(refpath, sizeof(refpath), ".git/%s", ref[i]) ==
		sizeof(refpath)){
- snprint(buf, sizeof(buf), "ref path too long: %s", ref[i]);
- goto error;
+ werrstr("ref path too long: %s", ref[i]);
+ goto out;
		}
		if(hasheq(&upd[i], &Zhash)){
			remove(refpath);
@@ -384,12 +426,12 @@
			continue;
		}
		if((o = readobject(upd[i])) == nil){
- snprint(buf, sizeof(buf), "update to nonexistent hash %H", upd[i]);
- goto error;
+ werrstr("update to nonexistent hash %H", upd[i]);
+ goto out;
		}
		if(o->type != GCommit){
- snprint(buf, sizeof(buf), "not commit: %H", upd[i]);
- goto error;
+ werrstr("not commit: %H", upd[i]);
+ goto out;
		}
		if(o->commit->mtime > newtm){
			newtm = o->commit->mtime;
@@ -397,13 +439,13 @@
		}
		unref(o);
		if((fd = create(refpath, OWRITE|OTRUNC, 0644)) == -1){
- snprint(buf, sizeof(buf), "open ref: %r");
- goto error;
+ werrstr("open ref: %r");
+ goto out;
		}
		if(fprint(fd, "%H", upd[i]) == -1){
- snprint(buf, sizeof(buf), "upate ref: %r");
+ werrstr("upate ref: %r");
			close(fd);
- goto error;
+ goto out;
		}
		close(fd);
	}
@@ -420,22 +462,30 @@
	 * use.  This should make us pick a useful default in
	 * those cases, instead of silently failing.
	 */
+ i = 0;
	if(resolveref(&h, "HEAD") == -1 && hadref == 0 && newidx != -1){
		if((fd = create(".git/HEAD", OWRITE|OTRUNC, 0644)) == -1){
- snprint(buf, sizeof(buf), "open HEAD: %r");
- goto error;
+ werrstr("open HEAD: %r");
+ goto out;
		}
- if(fprint(fd, "ref: %s", ref[0]) == -1){
- snprint(buf, sizeof(buf), "write HEAD ref: %r");
- goto error;
+ if(fprint(fd, "ref: %s", ref[i]) == -1){
+ werrstr("write HEAD ref: %r");
+ goto out;
		}
		close(fd);
	}
	ret = 0;
-error:
- fmtpkt(c, "ERR %s", buf);
- close(lockfd);
- werrstr(buf);
+out:
+ if(lockfd != -1)
+ close(lockfd);
+ if(!report)
+ return ret;
+ for(j = 0; j < nupd; j++){
+ if(i != j || ret == 0)
+ fmtpkt(c, "ok %s", ref[i]);
+ else
+ fmtpkt(c, "ng %s %r\n", ref[i]);
+ }
	return ret;
 }



Sun Jun 4 09:32:56 EDT 2023
diff 728cb9011f9612e969ec8747aa1de2a30959c38a uncommitted
--- a/rc/bin/fshalt
+++ b/rc/bin/fshalt
@@ -3,7 +3,6 @@
 # and optionally reboot
 rfork en
 reboot=no
-scram=no
 bootf=()
 if(~ $1 -r){
	reboot=yes
@@ -33,14 +32,8 @@
 h=`{ls /srv/hjfs*cmd >[2]/dev/null}
 s=`{awk '/^sd./ && /nvme/ {print substr($1,3,1)}' <'#S/sdctl'
 >[2]/dev/null}

-# for scram, don't scram other systems
+# don't halt other systems
 bind -b '#P' /dev >[2]/dev/null
-if(!  ~ $reboot yes){
- if(test -e '#P'/apm)
- scram=yes
- if(test -e '#P'/acpitbls -a -e '#P'/iow)
- scram=yes
-}

 # halting (binaries we run can't be on the fs we're halting)
 ramfs
@@ -52,7 +45,6 @@
 cp /bin/rc /tmp
 cp /bin/sed /tmp
 cp /bin/sleep /tmp
-cp /bin/scram /tmp
 cp /bin/test /tmp
 if(~ $#bootf 1){
	if(!  cp $bootf /tmp/bootf)
@@ -59,6 +51,11 @@
		exit 'failed to copy kernel'
	bootf=/bin/bootf
 }
+if not {
+ mkdir /tmp/aux
+ cp /bin/aux/acpi /tmp/aux
+}
+
 bind /tmp /rc
 bind /tmp /bin

@@ -88,8 +85,8 @@
	if not {
		if (test -e /dev/pmctl)
			echo power off >>/dev/pmctl
- if (~ $scram yes)
- scram
+
+ aux/acpi -H
		echo 'It''s now safe to turn off your computer'
	}
 }
--- a/sys/man/8/fshalt
+++ b/sys/man/8/fshalt
@@ -1,6 +1,6 @@
 .TH FSHALT 8
 .SH NAME
-fshalt, scram, reboot \- halt any local file systems and optionally shut down or
reboot the system
+fshalt, reboot \- halt any local file systems and optionally shut down or reboot
the system
 .SH SYNOPSIS
 .B fshalt
 [
@@ -14,8 +14,6 @@
 [
 .I kernelpath
 ]
-.br
-.B scram
 .SH DESCRIPTION
 .I Fshalt
 syncs and halts all local
@@ -30,9 +28,7 @@
 optionally starting
 .IR kernelpath .
 Else it will try to shut down the machine through
-.I /dev/pmctl
-(if available) or invoke
-.IR scram .
+.IR /dev/pmctl .
 The halting and rebooting is done by copying all necessary
 commands into a
 .IR ramfs (4)
@@ -48,24 +44,22 @@
 kernel directly instead of returning to the system rom.  (see
 .IR cons (3)).
 .PP
-.I Scram
-shuts down the machine it is invoked on.
 .SH SOURCE
 .B /rc/bin/fshalt
 .br
 .B /rc/bin/reboot
-.br
-.B /sys/src/cmd/scram.c
 .SH SEE ALSO
+.IR acpi (8),
 .IR cons (3),
 .IR reboot (8)
 .SH BUGS
-On standalone machines, it will be impossible to do anything if scram fails
-after invoking bare
+On standalone machines, it will be impossible to do anything if
+power off fails after invoking bare
 .IR fshalt .

-.I Scram
-is limited to the PC and requires APM or ACPI.
-.SH HISTORY
-.I Scram
-first appeared in 9front (May, 2011).
+.I Fshalt
+falls back to trying
+.I aux/acpi
+if writing to
+.B /dev/pmctl
+fails.
binary files /dev/null b/sys/src/cmd/aux/6.acpi differ
binary files /dev/null b/sys/src/cmd/aux/acpi.6 differ
--- a/sys/src/cmd/scram.c
+++ /dev/null
@@ -1,183 +1,0 @@
-#include <u.h>
-#include </386/include/ureg.h>
-#include <libc.h>
-#include <aml.h>
-
-int fd, iofd;
-struct Ureg u;
-ulong PM1a_CNT_BLK, PM1b_CNT_BLK, SLP_TYPa, SLP_TYPb;
-ulong GPE0_BLK, GPE1_BLK, GPE0_BLK_LEN, GPE1_BLK_LEN;
-enum {
- SLP_EN = 0x2000,
- SLP_TM = 0x1c00,
-};
-
-typedef struct Tbl Tbl;
-struct Tbl {
- uchar sig[4];
- uchar len[4];
- uchar rev;
- uchar csum;
- uchar oemid[6];
- uchar oemtid[8];
- uchar oemrev[4];
- uchar cid[4];
- uchar crev[4];
- uchar data[];
-};
-
-enum {
- Tblsz = 4+4+1+1+6+8+4+4+4,
-};
-
-static ulong
-get32(uchar *p){
- return p[3]<<24 | p[2]<<16 | p[1]<<8 | p[0];
-}
-
-void
-apm(void)
-{
- seek(fd, 0, 0);
- if(write(fd, &u, sizeof u) < 0)
- sysfatal("write: %r");
- seek(fd, 0, 0);
- if(read(fd, &u, sizeof u) < 0)
- sysfatal("read: %r");
- if(u.flags & 1)
- sysfatal("apm: %lux", (u.ax>>8) & 0xFF);
-}
-
-int
-loadacpi(void)
-{
- void *r, **rr;
- ulong l;
- Tbl *t;
- int n;
-
- amlinit();
- for(;;){
- t = malloc(sizeof(*t));
- if((n = readn(fd, t, Tblsz)) <= 0)
- break;
- if(n != Tblsz)
- return -1;
- l = get32(t->len);
- if(l < Tblsz)
- return -1;
- l -= Tblsz;
- t = realloc(t, sizeof(*t) + l);
- if(readn(fd, t->data, l) != l)
- return -1;
- if(memcmp("DSDT", t->sig, 4) == 0){
- amlintmask = (~0ULL) >> (t->rev <= 1)*32;
- amlload(t->data, l);
- }
- else if(memcmp("SSDT", t->sig, 4) == 0)
- amlload(t->data, l);
- else if(memcmp("FACP", t->sig, 4) == 0){
- PM1a_CNT_BLK = get32(((uchar*)t) + 64);
- PM1b_CNT_BLK = get32(((uchar*)t) + 68);
- GPE0_BLK = get32(((uchar*)t) + 80);
- GPE1_BLK = get32(((uchar*)t) + 84);
- GPE0_BLK_LEN = *(((uchar*)t) + 92);
- GPE1_BLK_LEN = *(((uchar*)t) + 93);
- }
- }
- if(amleval(amlwalk(amlroot, "_S5"), "", &r) < 0)
- return -1;
- if(amltag(r) != 'p' || amllen(r) < 2)
- return -1;
- rr = amlval(r);
- SLP_TYPa = amlint(rr[0]);
- SLP_TYPb = amlint(rr[1]);
- return 0;
-}
-
-void
-outw(long addr, ushort val)
-{
- uchar buf[2];
-
- if(addr == 0)
- return;
- buf[0] = val;
- buf[1] = val >> 8;
- pwrite(iofd, buf, 2, addr);
-}
-
-void
-wirecpu0(void)
-{
- char buf[128];
- int ctl;
-
- snprint(buf, sizeof(buf), "/proc/%d/ctl", getpid());
- if((ctl = open(buf, OWRITE)) < 0)
- return;
- write(ctl, "wired 0", 7);
- close(ctl);
-}
-
-void
-main(void)
-{
- int n;
-
- wirecpu0();
-
- if((fd = open("/dev/apm", ORDWR)) < 0)
- if((fd = open("#P/apm", ORDWR)) < 0)
- goto tryacpi;
-
- u.ax = 0x530E;
- u.bx = 0x0000;
- u.cx = 0x0102;
- apm();
- u.ax = 0x5307;
- u.bx = 0x0001;
- u.cx = 0x0003;
- apm();
-
-tryacpi:
- if((fd = open("/dev/acpitbls", OREAD)) < 0)
- if((fd = open("#P/acpitbls", OREAD)) < 0)
- goto fail;
- if((iofd = open("/dev/iow", OWRITE)) < 0)
- if((iofd = open("#P/iow", OWRITE)) < 0)
- goto fail;
- if(loadacpi() < 0)
- goto fail;
-
- /* disable GPEs */
- for(n = 0; GPE0_BLK > 0 && n < GPE0_BLK_LEN/2; n += 2){
- outw(GPE0_BLK + GPE0_BLK_LEN/2 + n, 0); /* EN */
- outw(GPE0_BLK + n, 0xffff); /* STS */
- }
- for(n = 0; GPE1_BLK > 0 && n < GPE1_BLK_LEN/2; n += 2){
- outw(GPE1_BLK + GPE1_BLK_LEN/2 + n, 0); /* EN */
- outw(GPE1_BLK + n, 0xffff); /* STS */
- }
-
- outw(PM1a_CNT_BLK, ((SLP_TYPa << 10) & SLP_TM) | SLP_EN);
- outw(PM1b_CNT_BLK, ((SLP_TYPb << 10) & SLP_TM) | SLP_EN);
- sleep(100);
-
- /*
- * The SetSystemSleeping() example from the ACPI spec
- * writes the same value in both registers.  But Linux/BSD
- * write distinct values from the _Sx package (like the
- * code above).  The _S5 package on a HP DC5700 is
- * Package(0x2){0x0, 0x7} and writing SLP_TYPa of 0 to
- * PM1a_CNT_BLK seems to have no effect but 0x7 seems
- * to work fine.  So trying the following as a last effort.
- */
- SLP_TYPa |= SLP_TYPb;
- outw(PM1a_CNT_BLK, ((SLP_TYPa << 10) & SLP_TM) | SLP_EN);
- outw(PM1b_CNT_BLK, ((SLP_TYPa << 10) & SLP_TM) | SLP_EN);
- sleep(100);
-
-fail:
- exits("scram");
-}


Sat Jun 3 21:40:00 EDT 2023
; cat /n/rachael/usr/bin/*|tput
0.00 B/s
0.00 B/s
10.67 KB/s
16.00 KB/s
19.20 KB/s
19.72 KB/s
21.48 KB/s
23.79 KB/s
23.82 KB/s
24.63 KB/s
25.30 KB/s
25.86 KB/s
26.33 KB/s
26.74 KB/s
27.09 KB/s
27.40 KB/s
28.61 KB/s
28.80 KB/s
28.96 KB/s
29.12 KB/s
28.87 KB/s
29.02 KB/s
29.49 KB/s
29.60 KB/s
29.37 KB/s
29.47 KB/s
29.57 KB/s
29.06 KB/s
28.33 KB/s
28.19 KB/s
28.57 KB/s
28.43 KB/s
28.54 KB/s
28.17 KB/s
27.36 KB/s

Sat Jun 3 21:07:46 EDT 2023
diff c6ca07ad4e2124c2e072ad63b54da494ac799312 uncommitted
--- a/sys/src/cmd/auth/factotum/rsa.c
+++ b/sys/src/cmd/auth/factotum/rsa.c
@@ -138,16 +138,19 @@
	default:
		return phaseerror(fss, "read");
	case CHavePub:
- if(s->key){
- closekey(s->key);
- s->key = nil;
- }
- mkkeyinfo(&ki, fss, nil);
- ki.skip = s->off;
- ki.noconf = 1;
- if(findkey(&s->key, &ki, nil) != RpcOk)
- return failure(fss, nil);
- s->off++;
+ do {
+ if(s->key){
+ closekey(s->key);
+ s->key = nil;
+ }
+ mkkeyinfo(&ki, fss, nil);
+ ki.skip = s->off;
+ ki.noconf = 1;
+ if(findkey(&s->key, &ki, nil) != RpcOk)
+ return failure(fss, nil);
+ s->off++;
+ /* need private key */
+ } while(s->key->privattr == nil);
		priv = s->key->priv;
		*n = snprint(va, *n, "%B %B", priv->pub.n, priv->pub.ek);
		return RpcOk;


prev | next