diff options
| author | Charles.Forsyth <devnull@localhost> | 2006-12-22 17:07:39 +0000 |
|---|---|---|
| committer | Charles.Forsyth <devnull@localhost> | 2006-12-22 17:07:39 +0000 |
| commit | 37da2899f40661e3e9631e497da8dc59b971cbd0 (patch) | |
| tree | cbc6d4680e347d906f5fa7fca73214418741df72 /appl/collab/collabsrv.b | |
| parent | 54bc8ff236ac10b3eaa928fd6bcfc0cdb2ba46ae (diff) | |
20060303a
Diffstat (limited to 'appl/collab/collabsrv.b')
| -rw-r--r-- | appl/collab/collabsrv.b | 176 |
1 files changed, 176 insertions, 0 deletions
diff --git a/appl/collab/collabsrv.b b/appl/collab/collabsrv.b new file mode 100644 index 00000000..f9f26011 --- /dev/null +++ b/appl/collab/collabsrv.b @@ -0,0 +1,176 @@ +implement Collabsrv; + +include "sys.m"; + sys: Sys; + +include "draw.m"; + +include "keyring.m"; +include "security.m"; + auth: Auth; + +include "srvmgr.m"; +include "proxy.m"; + +include "arg.m"; + +Collabsrv: module +{ + init: fn (ctxt: ref Draw->Context, args: list of string); +}; + +authinfo: ref Keyring->Authinfo; + +stderr: ref Sys->FD; +Srvreq, Srvreply: import Srvmgr; + +usage() +{ + sys->fprint(stderr, "usage: collabsrv [-k keyfile] [-n netaddress] [dir]\n"); + raise "fail:usage"; +} + +init(nil: ref Draw->Context, args: list of string) +{ + sys = load Sys Sys->PATH; + sys->pctl(Sys->NEWPGRP, nil); + stderr = sys->fildes(2); + + (err, user) := user(); + if (err != nil) + error(err); + + netaddr := "tcp!*!9999"; + keyfile := "/usr/" + user + "/keyring/default"; + root := "/services/collab"; + + arg := load Arg Arg->PATH; + arg->init(args); + while ((opt := arg->opt()) != 0) + case opt { + 'k' => + keyfile = arg->arg(); + if (keyfile == nil) + usage(); + if (keyfile[0] != '/' && (len keyfile < 2 || keyfile[0:2] != "./")) + keyfile = "/usr/" + user + "/keyring/" + keyfile; + 'n' => + netaddr = arg->arg(); + if (netaddr == nil) + usage(); + * => + usage(); + } + args = arg->argv(); + arg = nil; + if(args != nil) + root = hd args; + + auth = load Auth Auth->PATH; + if (auth == nil) + badmodule(Auth->PATH); + + kr := load Keyring Keyring->PATH; + if (kr == nil) + badmodule(Keyring->PATH); + + srvmgr := load Srvmgr Srvmgr->PATH; + if (srvmgr == nil) + badmodule(Srvmgr->PATH); + + err = auth->init(); + if (err != nil) + error(sys->sprint("failed to init Auth: %s", err)); + + authinfo = kr->readauthinfo(keyfile); + kr = nil; + if (authinfo == nil) + error(sys->sprint("cannot read %s: %r", keyfile)); + + netaddr = netmkaddr(netaddr, "tcp", "9999"); + (ok, c) := sys->announce(netaddr); + if (ok < 0) + error(sys->sprint("cannot announce %s: %r", netaddr)); + + rc: chan of ref Srvreq; + (err, rc) = srvmgr->init(root); + if (err != nil) + error(err); + + sys->print("Srvmgr started\n"); + + for (;;) { + (okl, nc) := sys->listen(c); + if (okl < 0) { + sys->print("listen failed: %r\n"); + sys->sleep(1000); + return; + } + fd := sys->open(nc.dir+"/data", Sys->ORDWR); + if(nc.cfd != nil) + sys->fprint(nc.cfd, "keepalive"); + nc.cfd = nil; + if (fd != nil) + spawn newclient(rc, fd, root); + fd = nil; + } +} + +badmodule(path: string) +{ + error(sys->sprint("cannot load module %s: %r", path)); +} + +error(s: string) +{ + sys->fprint(stderr, "collabsrv: %s\n", s); + raise "fail:error"; +} + +user(): (string, string) +{ + sys = load Sys Sys->PATH; + fd := sys->open("/dev/user", sys->OREAD); + if(fd == nil) + return (sys->sprint("can't open /dev/user: %r"), nil); + buf := array[128] of byte; + n := sys->read(fd, buf, len buf); + if(n <= 0) + return (sys->sprint("failed to read /dev/user: %r"), nil); + return (nil, string buf[0:n]); +} + +newclient(rc: chan of ref Srvreq, fd: ref Sys->FD, root: string) +{ + algs := "none" :: "clear" :: "md4" :: "md5" :: nil; + sys->print("new client\n"); + proxy := load Proxy Proxy->PATH; + if (proxy == nil) { + sys->fprint(stderr, "collabsrv: cannot load %s: %r\n", Proxy->PATH); + return; + } + sys->pctl(Sys->NEWPGRP|Sys->FORKNS|Sys->FORKENV, nil); + s := ""; + (fd, s) = auth->server(algs, authinfo, fd, 1); + if (fd == nil){ + sys->fprint(stderr, "collabsrv: cannot authenticate: %s\n", s); + return; + } + sys->fprint(stderr, "uname: %s\n", s); + spawn proxy->init(root, fd, rc, s); +} + +netmkaddr(addr, net, svc: string): string +{ + if(net == nil) + net = "net"; + (n, l) := sys->tokenize(addr, "!"); + if(n <= 1){ + if(svc== nil) + return sys->sprint("%s!%s", net, addr); + return sys->sprint("%s!%s!%s", net, addr, svc); + } + if(svc == nil || n > 2) + return addr; + return sys->sprint("%s!%s", addr, svc); +} |
