1*37da2899SCharles.Forsythimplement Create; 2*37da2899SCharles.Forsyth 3*37da2899SCharles.Forsythinclude "sys.m"; 4*37da2899SCharles.Forsyth sys: Sys; 5*37da2899SCharles.Forsyth Dir, sprint, fprint: import sys; 6*37da2899SCharles.Forsythinclude "draw.m"; 7*37da2899SCharles.Forsythinclude "bufio.m"; 8*37da2899SCharles.Forsyth bufio: Bufio; 9*37da2899SCharles.Forsyth Iobuf: import bufio; 10*37da2899SCharles.Forsythinclude "string.m"; 11*37da2899SCharles.Forsyth str: String; 12*37da2899SCharles.Forsythinclude "arg.m"; 13*37da2899SCharles.Forsyth arg: Arg; 14*37da2899SCharles.Forsythinclude "daytime.m"; 15*37da2899SCharles.Forsythinclude "keyring.m"; 16*37da2899SCharles.Forsyth keyring : Keyring; 17*37da2899SCharles.Forsythinclude "sh.m"; 18*37da2899SCharles.Forsythinclude "wrap.m"; 19*37da2899SCharles.Forsyth wrap : Wrap; 20*37da2899SCharles.Forsythinclude "arch.m"; 21*37da2899SCharles.Forsyth arch : Arch; 22*37da2899SCharles.Forsythinclude "proto.m"; 23*37da2899SCharles.Forsyth proto : Proto; 24*37da2899SCharles.Forsythinclude "protocaller.m"; 25*37da2899SCharles.Forsyth protocaller : Protocaller; 26*37da2899SCharles.Forsyth 27*37da2899SCharles.ForsythWARN, ERROR, FATAL : import Protocaller; 28*37da2899SCharles.Forsyth 29*37da2899SCharles.ForsythCreate: module{ 30*37da2899SCharles.Forsyth init: fn(nil: ref Draw->Context, nil: list of string); 31*37da2899SCharles.Forsyth protofile: fn(new : string, old : string, d : ref Sys->Dir); 32*37da2899SCharles.Forsyth protoerr: fn(lev : int, line : int, err : string); 33*37da2899SCharles.Forsyth}; 34*37da2899SCharles.Forsyth 35*37da2899SCharles.Forsythbout: ref Iobuf; # stdout when writing archive 36*37da2899SCharles.Forsythprotof: string; 37*37da2899SCharles.Forsythnotesf: string; 38*37da2899SCharles.Forsytholdroot: string; 39*37da2899SCharles.Forsythbuf: array of byte; 40*37da2899SCharles.Forsythbuflen := 1024-8; 41*37da2899SCharles.Forsythverb: int; 42*37da2899SCharles.Forsythxflag: int; 43*37da2899SCharles.Forsythstderr: ref Sys->FD; 44*37da2899SCharles.Forsythuid, gid : string; 45*37da2899SCharles.Forsythdesc : string; 46*37da2899SCharles.Forsythpass : int; 47*37da2899SCharles.Forsythupdate : int; 48*37da2899SCharles.Forsythmd5s : ref Keyring->DigestState; 49*37da2899SCharles.Forsythw : ref Wrap->Wrapped; 50*37da2899SCharles.Forsythroot := "/"; 51*37da2899SCharles.Forsythprefix, notprefix: list of string; 52*37da2899SCharles.Forsythonlist: list of (string, string); # NEW 53*37da2899SCharles.Forsythremfile: string; 54*37da2899SCharles.Forsyth 55*37da2899SCharles.Forsythn2o(n: string): string 56*37da2899SCharles.Forsyth{ 57*37da2899SCharles.Forsyth for(onl := onlist; onl != nil; onl = tl onl) 58*37da2899SCharles.Forsyth if((hd onl).t1 == n) 59*37da2899SCharles.Forsyth return (hd onl).t0; 60*37da2899SCharles.Forsyth return n; 61*37da2899SCharles.Forsyth} 62*37da2899SCharles.Forsyth 63*37da2899SCharles.Forsythinit(nil: ref Draw->Context, args: list of string) 64*37da2899SCharles.Forsyth{ 65*37da2899SCharles.Forsyth sys = load Sys Sys->PATH; 66*37da2899SCharles.Forsyth bufio = load Bufio Bufio->PATH; 67*37da2899SCharles.Forsyth str = load String String->PATH; 68*37da2899SCharles.Forsyth arg = load Arg Arg->PATH; 69*37da2899SCharles.Forsyth wrap = load Wrap Wrap->PATH; 70*37da2899SCharles.Forsyth wrap->init(bufio); 71*37da2899SCharles.Forsyth arch = load Arch Arch->PATH; 72*37da2899SCharles.Forsyth arch->init(bufio); 73*37da2899SCharles.Forsyth daytime := load Daytime Daytime->PATH; 74*37da2899SCharles.Forsyth now := daytime->now(); 75*37da2899SCharles.Forsyth # { 76*37da2899SCharles.Forsyth # for(i := 0; i < 21; i++){ 77*37da2899SCharles.Forsyth # n := now+(i-9)*100000000; 78*37da2899SCharles.Forsyth # sys->print("%d -> %s\n", n, wrap->now2string(n)); 79*37da2899SCharles.Forsyth # if(wrap->string2now(wrap->now2string(n)) != n) 80*37da2899SCharles.Forsyth # sys->print("%d wrong\n", n); 81*37da2899SCharles.Forsyth # } 82*37da2899SCharles.Forsyth # } 83*37da2899SCharles.Forsyth daytime = nil; 84*37da2899SCharles.Forsyth proto = load Proto Proto->PATH; 85*37da2899SCharles.Forsyth protocaller = load Protocaller "$self"; 86*37da2899SCharles.Forsyth 87*37da2899SCharles.Forsyth sys->pctl(Sys->NEWPGRP|Sys->FORKNS|Sys->FORKFD, nil); 88*37da2899SCharles.Forsyth stderr = sys->fildes(2); 89*37da2899SCharles.Forsyth if(arg == nil) 90*37da2899SCharles.Forsyth error(sys->sprint("can't load %s: %r", Arg->PATH)); 91*37da2899SCharles.Forsyth name := ""; 92*37da2899SCharles.Forsyth desc = "inferno"; 93*37da2899SCharles.Forsyth tostdout := 0; 94*37da2899SCharles.Forsyth not := 0; 95*37da2899SCharles.Forsyth arg->init(args); 96*37da2899SCharles.Forsyth while((c := arg->opt()) != 0) 97*37da2899SCharles.Forsyth case c { 98*37da2899SCharles.Forsyth 'n' => 99*37da2899SCharles.Forsyth not = 1; 100*37da2899SCharles.Forsyth 'o' => 101*37da2899SCharles.Forsyth tostdout = 1; 102*37da2899SCharles.Forsyth 'p' => 103*37da2899SCharles.Forsyth protof = reqarg("proto file (-p)"); 104*37da2899SCharles.Forsyth 'r' => 105*37da2899SCharles.Forsyth root = reqarg("root directory (-r)"); 106*37da2899SCharles.Forsyth 's' => 107*37da2899SCharles.Forsyth oldroot = reqarg("source directory (-d)"); 108*37da2899SCharles.Forsyth 'u' => 109*37da2899SCharles.Forsyth update = 1; 110*37da2899SCharles.Forsyth 'v' => 111*37da2899SCharles.Forsyth verb = 1; 112*37da2899SCharles.Forsyth 'x' => 113*37da2899SCharles.Forsyth xflag = 1; 114*37da2899SCharles.Forsyth 'N' => 115*37da2899SCharles.Forsyth uid = reqarg("user name (-U)"); 116*37da2899SCharles.Forsyth 'G' => 117*37da2899SCharles.Forsyth gid = reqarg("group name (-G)"); 118*37da2899SCharles.Forsyth 'd' or 'D' => 119*37da2899SCharles.Forsyth desc = reqarg("product description (-D)"); 120*37da2899SCharles.Forsyth 't' => 121*37da2899SCharles.Forsyth rt := reqarg("package time (-t)"); 122*37da2899SCharles.Forsyth now = int rt; 123*37da2899SCharles.Forsyth 'i' => 124*37da2899SCharles.Forsyth notesf = reqarg("file (-i)"); 125*37da2899SCharles.Forsyth 'R' => 126*37da2899SCharles.Forsyth remfile = reqarg("remove file (-R)"); 127*37da2899SCharles.Forsyth 'P' => 128*37da2899SCharles.Forsyth arch->addperms(0); 129*37da2899SCharles.Forsyth * => 130*37da2899SCharles.Forsyth usage(); 131*37da2899SCharles.Forsyth } 132*37da2899SCharles.Forsyth 133*37da2899SCharles.Forsyth args = arg->argv(); 134*37da2899SCharles.Forsyth if(args == nil) 135*37da2899SCharles.Forsyth usage(); 136*37da2899SCharles.Forsyth if (tostdout || xflag) { 137*37da2899SCharles.Forsyth bout = bufio->fopen(sys->fildes(1), Sys->OWRITE); 138*37da2899SCharles.Forsyth if(bout == nil) 139*37da2899SCharles.Forsyth error(sys->sprint("can't open standard output for archive: %r")); 140*37da2899SCharles.Forsyth } 141*37da2899SCharles.Forsyth else { 142*37da2899SCharles.Forsyth # ar := sys->sprint("%ud", now); 143*37da2899SCharles.Forsyth ar := wrap->now2string(now, 0); 144*37da2899SCharles.Forsyth bout = bufio->create(ar, Sys->OWRITE, 8r664); 145*37da2899SCharles.Forsyth if(bout == nil) 146*37da2899SCharles.Forsyth error(sys->sprint("can't create %s for archive: %r", ar)); 147*37da2899SCharles.Forsyth sys->print("archiving package %s to %s\n", hd args, ar); 148*37da2899SCharles.Forsyth } 149*37da2899SCharles.Forsyth buf = array [buflen] of byte; 150*37da2899SCharles.Forsyth name = hd args; 151*37da2899SCharles.Forsyth if(update){ 152*37da2899SCharles.Forsyth if(not) 153*37da2899SCharles.Forsyth notprefix = tl args; 154*37da2899SCharles.Forsyth else 155*37da2899SCharles.Forsyth prefix = tl args; 156*37da2899SCharles.Forsyth } 157*37da2899SCharles.Forsyth else if (tl args != nil) 158*37da2899SCharles.Forsyth fatal("only one name allowed"); 159*37da2899SCharles.Forsyth if (!xflag) 160*37da2899SCharles.Forsyth digest := wrapinit(name, now); 161*37da2899SCharles.Forsyth fprint(stderr, "processing %s\n", protof); 162*37da2899SCharles.Forsyth proto->rdproto(protof, oldroot, protocaller); 163*37da2899SCharles.Forsyth if (!xflag) 164*37da2899SCharles.Forsyth wrapend(digest); 165*37da2899SCharles.Forsyth if (!xflag) 166*37da2899SCharles.Forsyth fprint(stderr, "file system made\n"); 167*37da2899SCharles.Forsyth arch->putend(bout); 168*37da2899SCharles.Forsyth exits(); 169*37da2899SCharles.Forsyth} 170*37da2899SCharles.Forsyth 171*37da2899SCharles.Forsythprotofile(new : string, old : string, d : ref Sys->Dir) 172*37da2899SCharles.Forsyth{ 173*37da2899SCharles.Forsyth if(xflag && bout != nil){ 174*37da2899SCharles.Forsyth bout.puts(sys->sprint("%s\t%d\t%bd\n", new, d.mtime, d.length)); 175*37da2899SCharles.Forsyth return; 176*37da2899SCharles.Forsyth } 177*37da2899SCharles.Forsyth d.uid = uid; 178*37da2899SCharles.Forsyth d.gid = gid; 179*37da2899SCharles.Forsyth if (!(d.mode & Sys->DMDIR)) { 180*37da2899SCharles.Forsyth # if(verb) 181*37da2899SCharles.Forsyth # fprint(stderr, "%s\n", new); 182*37da2899SCharles.Forsyth f := sys->open(old, Sys->OREAD); 183*37da2899SCharles.Forsyth if(f == nil){ 184*37da2899SCharles.Forsyth warn(sys->sprint("can't open %s: %r", old)); 185*37da2899SCharles.Forsyth return; 186*37da2899SCharles.Forsyth } 187*37da2899SCharles.Forsyth } 188*37da2899SCharles.Forsyth mkarch(new, old, d); 189*37da2899SCharles.Forsyth} 190*37da2899SCharles.Forsyth 191*37da2899SCharles.Forsythprotoerr(lev : int, line : int, err : string) 192*37da2899SCharles.Forsyth{ 193*37da2899SCharles.Forsyth s := "line " + string line + " : " + err; 194*37da2899SCharles.Forsyth case lev { 195*37da2899SCharles.Forsyth WARN => warn(s); 196*37da2899SCharles.Forsyth ERROR => error(s); 197*37da2899SCharles.Forsyth FATAL => fatal(s); 198*37da2899SCharles.Forsyth } 199*37da2899SCharles.Forsyth} 200*37da2899SCharles.Forsyth 201*37da2899SCharles.Forsythquit() 202*37da2899SCharles.Forsyth{ 203*37da2899SCharles.Forsyth if(bout != nil) 204*37da2899SCharles.Forsyth bout.flush(); 205*37da2899SCharles.Forsyth exits(); 206*37da2899SCharles.Forsyth} 207*37da2899SCharles.Forsyth 208*37da2899SCharles.Forsythreqarg(what: string): string 209*37da2899SCharles.Forsyth{ 210*37da2899SCharles.Forsyth if((o := arg->arg()) == nil){ 211*37da2899SCharles.Forsyth sys->fprint(stderr, "missing %s\n", what); 212*37da2899SCharles.Forsyth exits(); 213*37da2899SCharles.Forsyth } 214*37da2899SCharles.Forsyth return o; 215*37da2899SCharles.Forsyth} 216*37da2899SCharles.Forsyth 217*37da2899SCharles.Forsythputhdr(f : string, d: ref Dir) 218*37da2899SCharles.Forsyth{ 219*37da2899SCharles.Forsyth if (d.mode & Sys->DMDIR) 220*37da2899SCharles.Forsyth d.length = big 0; 221*37da2899SCharles.Forsyth arch->puthdr(bout, f, d); 222*37da2899SCharles.Forsyth} 223*37da2899SCharles.Forsyth 224*37da2899SCharles.Forsytherror(s: string) 225*37da2899SCharles.Forsyth{ 226*37da2899SCharles.Forsyth fprint(stderr, "%s: %s\n", protof, s); 227*37da2899SCharles.Forsyth quit(); 228*37da2899SCharles.Forsyth} 229*37da2899SCharles.Forsyth 230*37da2899SCharles.Forsythfatal(s: string) 231*37da2899SCharles.Forsyth{ 232*37da2899SCharles.Forsyth fprint(stderr, "fatal: %s\n", s); 233*37da2899SCharles.Forsyth exits(); 234*37da2899SCharles.Forsyth} 235*37da2899SCharles.Forsyth 236*37da2899SCharles.Forsythwarn(s: string) 237*37da2899SCharles.Forsyth{ 238*37da2899SCharles.Forsyth fprint(stderr, "%s: %s\n", protof, s); 239*37da2899SCharles.Forsyth} 240*37da2899SCharles.Forsyth 241*37da2899SCharles.Forsythusage() 242*37da2899SCharles.Forsyth{ 243*37da2899SCharles.Forsyth fprint(stderr, "usage: install/create [-ovx] [-N uid] [-G gid] [-r root] [-d desc] [-s src-fs] [-p proto] name\n"); 244*37da2899SCharles.Forsyth fprint(stderr, "or install/create -u [-ovx] [-N uid] [-G gid] [-r root] [-d desc] [-s src-fs] [-p proto] old-package [prefix ...]\n"); 245*37da2899SCharles.Forsyth exits(); 246*37da2899SCharles.Forsyth} 247*37da2899SCharles.Forsyth 248*37da2899SCharles.Forsythwrapinit(name : string, t : int) : array of byte 249*37da2899SCharles.Forsyth{ 250*37da2899SCharles.Forsyth rmfile : string; 251*37da2899SCharles.Forsyth rmfd: ref Sys->FD; 252*37da2899SCharles.Forsyth 253*37da2899SCharles.Forsyth if (uid == nil) 254*37da2899SCharles.Forsyth uid = "inferno"; 255*37da2899SCharles.Forsyth if (gid == nil) 256*37da2899SCharles.Forsyth gid = "inferno"; 257*37da2899SCharles.Forsyth if (update) { 258*37da2899SCharles.Forsyth w = wrap->openwraphdr(name, root, nil, 0); 259*37da2899SCharles.Forsyth if (w == nil) 260*37da2899SCharles.Forsyth fatal("no such package found"); 261*37da2899SCharles.Forsyth # ignore any updates - NEW commented out 262*37da2899SCharles.Forsyth # while (w.nu > 0 && w.u[w.nu-1].typ == wrap->UPD) 263*37da2899SCharles.Forsyth # w.nu--; 264*37da2899SCharles.Forsyth 265*37da2899SCharles.Forsyth # w.nu = 1; NEW commented out 266*37da2899SCharles.Forsyth if (protof == nil) 267*37da2899SCharles.Forsyth protof = w.u[0].dir + "/proto"; 268*37da2899SCharles.Forsyth name = w.name; 269*37da2899SCharles.Forsyth } 270*37da2899SCharles.Forsyth else { 271*37da2899SCharles.Forsyth if (protof == nil) 272*37da2899SCharles.Forsyth fatal("proto file missing"); 273*37da2899SCharles.Forsyth } 274*37da2899SCharles.Forsyth (md5file, md5fd) := opentemp("wrap.md5", t); 275*37da2899SCharles.Forsyth if (md5fd == nil) 276*37da2899SCharles.Forsyth fatal(sys->sprint("cannot create %s", md5file)); 277*37da2899SCharles.Forsyth keyring = load Keyring Keyring->PATH; 278*37da2899SCharles.Forsyth md5s = keyring->md5(nil, 0, nil, nil); 279*37da2899SCharles.Forsyth md5b := bufio->fopen(md5fd, Bufio->OWRITE); 280*37da2899SCharles.Forsyth if (md5b == nil) 281*37da2899SCharles.Forsyth fatal(sys->sprint("cannot open %s", md5file)); 282*37da2899SCharles.Forsyth fprint(stderr, "wrap pass %s\n", protof); 283*37da2899SCharles.Forsyth obout := bout; 284*37da2899SCharles.Forsyth bout = md5b; 285*37da2899SCharles.Forsyth pass = 0; 286*37da2899SCharles.Forsyth proto->rdproto(protof, oldroot, protocaller); 287*37da2899SCharles.Forsyth bout.flush(); 288*37da2899SCharles.Forsyth bout = md5b = nil; 289*37da2899SCharles.Forsyth digest := array[keyring->MD5dlen] of { * => byte 0 }; 290*37da2899SCharles.Forsyth keyring->md5(nil, 0, digest, md5s); 291*37da2899SCharles.Forsyth md5s = nil; 292*37da2899SCharles.Forsyth (md5sort, md5sfd) := opentemp("wrap.md5s", t); 293*37da2899SCharles.Forsyth if (md5sfd == nil) 294*37da2899SCharles.Forsyth fatal(sys->sprint("cannot create %s", md5sort)); 295*37da2899SCharles.Forsyth endc := chan of int; 296*37da2899SCharles.Forsyth md5fd = nil; # close md5file 297*37da2899SCharles.Forsyth spawn fsort(md5sfd, md5file, endc); 298*37da2899SCharles.Forsyth md5sfd = nil; 299*37da2899SCharles.Forsyth res := <- endc; 300*37da2899SCharles.Forsyth if (res < 0) 301*37da2899SCharles.Forsyth fatal("sort failed"); 302*37da2899SCharles.Forsyth if (update) { 303*37da2899SCharles.Forsyth (rmfile, rmfd) = opentemp("wrap.rm", t); 304*37da2899SCharles.Forsyth if (rmfd == nil) 305*37da2899SCharles.Forsyth fatal(sys->sprint("cannot create %s", rmfile)); 306*37da2899SCharles.Forsyth rmed: list of string; 307*37da2899SCharles.Forsyth for(i := w.nu-1; i >= 0; i--){ # NEW does loop 308*37da2899SCharles.Forsyth w.u[i].bmd5.seek(big 0, Bufio->SEEKSTART); 309*37da2899SCharles.Forsyth while ((p := w.u[i].bmd5.gets('\n')) != nil) { 310*37da2899SCharles.Forsyth if(prefix != nil && !wrap->match(p, prefix)) 311*37da2899SCharles.Forsyth continue; 312*37da2899SCharles.Forsyth if(notprefix != nil && !wrap->notmatch(p, notprefix)) 313*37da2899SCharles.Forsyth continue; 314*37da2899SCharles.Forsyth (q, nil) := str->splitl(p, " "); 315*37da2899SCharles.Forsyth q = pathcat(root, q); 316*37da2899SCharles.Forsyth (ok, nil) := sys->stat(q); 317*37da2899SCharles.Forsyth if(ok < 0) 318*37da2899SCharles.Forsyth (ok, nil) = sys->stat(n2o(q)); 319*37da2899SCharles.Forsyth if (len q >= 7 && q[len q - 7:] == "emu.new") # quick hack for now 320*37da2899SCharles.Forsyth continue; 321*37da2899SCharles.Forsyth if (ok < 0){ 322*37da2899SCharles.Forsyth for(r := rmed; r != nil; r = tl r) # NEW to avoid duplication 323*37da2899SCharles.Forsyth if(hd r == q) 324*37da2899SCharles.Forsyth break; 325*37da2899SCharles.Forsyth if(r == nil){ 326*37da2899SCharles.Forsyth # sys->fprint(rmfd, "%s\n", q); 327*37da2899SCharles.Forsyth rmed = q :: rmed; 328*37da2899SCharles.Forsyth } 329*37da2899SCharles.Forsyth } 330*37da2899SCharles.Forsyth } 331*37da2899SCharles.Forsyth } 332*37da2899SCharles.Forsyth for(r := rmed; r != nil; r = tl r) 333*37da2899SCharles.Forsyth sys->fprint(rmfd, "%s\n", hd r); 334*37da2899SCharles.Forsyth if(remfile != nil){ 335*37da2899SCharles.Forsyth rfd := sys->open(remfile, Sys->OREAD); 336*37da2899SCharles.Forsyth rbuf := array[128] of byte; 337*37da2899SCharles.Forsyth for(;;){ 338*37da2899SCharles.Forsyth n := sys->read(rfd, rbuf, 128); 339*37da2899SCharles.Forsyth if(n <= 0) 340*37da2899SCharles.Forsyth break; 341*37da2899SCharles.Forsyth sys->write(rmfd, rbuf, n); 342*37da2899SCharles.Forsyth } 343*37da2899SCharles.Forsyth } 344*37da2899SCharles.Forsyth rmfd = nil; 345*37da2899SCharles.Forsyth rmed = nil; 346*37da2899SCharles.Forsyth } 347*37da2899SCharles.Forsyth bout = obout; 348*37da2899SCharles.Forsyth if (update) 349*37da2899SCharles.Forsyth wrap->putwrap(bout, name, t, desc, w.tfull, prefix == nil && notprefix == nil, uid, gid); 350*37da2899SCharles.Forsyth else 351*37da2899SCharles.Forsyth wrap->putwrap(bout, name, t, desc, 0, 1, uid, gid); 352*37da2899SCharles.Forsyth wrap->putwrapfile(bout, name, t, "proto", protof, uid, gid); 353*37da2899SCharles.Forsyth wrap->putwrapfile(bout, name, t, "md5sum", md5sort, uid, gid); 354*37da2899SCharles.Forsyth if (update) 355*37da2899SCharles.Forsyth wrap->putwrapfile(bout, name, t, "remove", rmfile, uid, gid); 356*37da2899SCharles.Forsyth if(notesf != nil) 357*37da2899SCharles.Forsyth wrap->putwrapfile(bout, name, t, "notes", notesf, uid, gid); 358*37da2899SCharles.Forsyth md5s = keyring->md5(nil, 0, nil, nil); 359*37da2899SCharles.Forsyth pass = 1; 360*37da2899SCharles.Forsyth return digest; 361*37da2899SCharles.Forsyth} 362*37da2899SCharles.Forsyth 363*37da2899SCharles.Forsythwrapend(digest : array of byte) 364*37da2899SCharles.Forsyth{ 365*37da2899SCharles.Forsyth digest0 := array[keyring->MD5dlen] of { * => byte 0 }; 366*37da2899SCharles.Forsyth keyring->md5(nil, 0, digest0, md5s); 367*37da2899SCharles.Forsyth md5s = nil; 368*37da2899SCharles.Forsyth if (wrap->memcmp(digest, digest0, keyring->MD5dlen) != 0) 369*37da2899SCharles.Forsyth warn(sys->sprint("files changed underfoot %s %s", wrap->md5conv(digest), wrap->md5conv(digest0))); 370*37da2899SCharles.Forsyth} 371*37da2899SCharles.Forsyth 372*37da2899SCharles.Forsythmkarch(new : string, old : string, d : ref Dir) 373*37da2899SCharles.Forsyth{ 374*37da2899SCharles.Forsyth if(pass == 0 && old != new) 375*37da2899SCharles.Forsyth onlist = (old, new) :: onlist; 376*37da2899SCharles.Forsyth if(prefix != nil && !wrap->match(new, prefix)) 377*37da2899SCharles.Forsyth return; 378*37da2899SCharles.Forsyth if(notprefix != nil && !wrap->notmatch(new, notprefix)) 379*37da2899SCharles.Forsyth return; 380*37da2899SCharles.Forsyth digest := array[keyring->MD5dlen] of { * => byte 0 }; 381*37da2899SCharles.Forsyth wrap->md5file(old, digest); 382*37da2899SCharles.Forsyth (ok, nil) := wrap->getfileinfo(w, new, digest, nil, nil); 383*37da2899SCharles.Forsyth if (ok >= 0) 384*37da2899SCharles.Forsyth return; 385*37da2899SCharles.Forsyth n := array of byte new; 386*37da2899SCharles.Forsyth keyring->md5(n, len n, nil, md5s); 387*37da2899SCharles.Forsyth if (pass == 0) { 388*37da2899SCharles.Forsyth bout.puts(sys->sprint("%s %s\n", new, wrap->md5conv(digest))); 389*37da2899SCharles.Forsyth return; 390*37da2899SCharles.Forsyth } 391*37da2899SCharles.Forsyth if(verb) 392*37da2899SCharles.Forsyth fprint(stderr, "%s\n", new); 393*37da2899SCharles.Forsyth puthdr(new, d); 394*37da2899SCharles.Forsyth if(!(d.mode & Sys->DMDIR)) { 395*37da2899SCharles.Forsyth err := arch->putfile(bout, old, int d.length); 396*37da2899SCharles.Forsyth if (err != nil) 397*37da2899SCharles.Forsyth warn(err); 398*37da2899SCharles.Forsyth } 399*37da2899SCharles.Forsyth} 400*37da2899SCharles.Forsyth 401*37da2899SCharles.Forsythfsort(fd : ref Sys->FD, file : string, c : chan of int) 402*37da2899SCharles.Forsyth{ 403*37da2899SCharles.Forsyth sys->pctl(Sys->FORKFD, nil); 404*37da2899SCharles.Forsyth sys->dup(fd.fd, 1); 405*37da2899SCharles.Forsyth cmd := "/dis/sort.dis"; 406*37da2899SCharles.Forsyth m := load Command cmd; 407*37da2899SCharles.Forsyth if(m == nil) { 408*37da2899SCharles.Forsyth c <-= -1; 409*37da2899SCharles.Forsyth return; 410*37da2899SCharles.Forsyth } 411*37da2899SCharles.Forsyth m->init(nil, cmd :: file :: nil); 412*37da2899SCharles.Forsyth c <-= 0; 413*37da2899SCharles.Forsyth} 414*37da2899SCharles.Forsyth 415*37da2899SCharles.Forsythtmpfiles: list of string; 416*37da2899SCharles.Forsyth 417*37da2899SCharles.Forsythopentemp(prefix: string, t: int): (string, ref Sys->FD) 418*37da2899SCharles.Forsyth{ 419*37da2899SCharles.Forsyth name := sys->sprint("/tmp/%s.%ud.%d", prefix, t, sys->pctl(0, nil)); 420*37da2899SCharles.Forsyth fd := sys->create(name, Sys->ORDWR, 8r666); 421*37da2899SCharles.Forsyth # fd := sys->create(name, Sys->ORDWR | Sys->ORCLOSE, 8r666); not on Nt 422*37da2899SCharles.Forsyth tmpfiles = name :: tmpfiles; 423*37da2899SCharles.Forsyth return (name, fd); 424*37da2899SCharles.Forsyth} 425*37da2899SCharles.Forsyth 426*37da2899SCharles.Forsythexits() 427*37da2899SCharles.Forsyth{ 428*37da2899SCharles.Forsyth wrap->end(); 429*37da2899SCharles.Forsyth for( ; tmpfiles != nil; tmpfiles = tl tmpfiles) 430*37da2899SCharles.Forsyth sys->remove(hd tmpfiles); 431*37da2899SCharles.Forsyth exit; 432*37da2899SCharles.Forsyth} 433*37da2899SCharles.Forsyth 434*37da2899SCharles.Forsythpathcat(s : string, t : string) : string 435*37da2899SCharles.Forsyth{ 436*37da2899SCharles.Forsyth if (s == nil) return t; 437*37da2899SCharles.Forsyth if (t == nil) return s; 438*37da2899SCharles.Forsyth slashs := s[len s - 1] == '/'; 439*37da2899SCharles.Forsyth slasht := t[0] == '/'; 440*37da2899SCharles.Forsyth if (slashs && slasht) 441*37da2899SCharles.Forsyth return s + t[1:]; 442*37da2899SCharles.Forsyth if (!slashs && !slasht) 443*37da2899SCharles.Forsyth return s + "/" + t; 444*37da2899SCharles.Forsyth return s + t; 445*37da2899SCharles.Forsyth} 446