1*9a747e4fSDavid du Colombier #include <u.h> 2*9a747e4fSDavid du Colombier #include <libc.h> 3*9a747e4fSDavid du Colombier #include <bio.h> 4*9a747e4fSDavid du Colombier #include <ip.h> 5*9a747e4fSDavid du Colombier #include <plumb.h> 6*9a747e4fSDavid du Colombier #include <thread.h> 7*9a747e4fSDavid du Colombier #include <fcall.h> 8*9a747e4fSDavid du Colombier #include <9p.h> 9*9a747e4fSDavid du Colombier #include <mp.h> 10*9a747e4fSDavid du Colombier #include <libsec.h> 11*9a747e4fSDavid du Colombier #include "dat.h" 12*9a747e4fSDavid du Colombier #include "fns.h" 13*9a747e4fSDavid du Colombier 14*9a747e4fSDavid du Colombier static int tlsdial(char*, char*, char*, int*, int); 15*9a747e4fSDavid du Colombier 16*9a747e4fSDavid du Colombier static long 17*9a747e4fSDavid du Colombier t(Ioproc *io, void (*op)(Ioproc*), int n, ...) 18*9a747e4fSDavid du Colombier { 19*9a747e4fSDavid du Colombier int i, ret; 20*9a747e4fSDavid du Colombier va_list arg; 21*9a747e4fSDavid du Colombier 22*9a747e4fSDavid du Colombier assert(!io->inuse); 23*9a747e4fSDavid du Colombier io->inuse = 1; 24*9a747e4fSDavid du Colombier io->op = op; 25*9a747e4fSDavid du Colombier va_start(arg, n); 26*9a747e4fSDavid du Colombier for(i=0; i<n; i++) 27*9a747e4fSDavid du Colombier io->arg[i] = va_arg(arg, long); 28*9a747e4fSDavid du Colombier sendp(io->c, io); 29*9a747e4fSDavid du Colombier recvp(io->c); 30*9a747e4fSDavid du Colombier ret = io->ret; 31*9a747e4fSDavid du Colombier if(ret < 0) 32*9a747e4fSDavid du Colombier errstr(io->err, sizeof io->err); 33*9a747e4fSDavid du Colombier io->inuse = 0; 34*9a747e4fSDavid du Colombier return ret; 35*9a747e4fSDavid du Colombier } 36*9a747e4fSDavid du Colombier 37*9a747e4fSDavid du Colombier static void 38*9a747e4fSDavid du Colombier t2(Ioproc *io, int ret) 39*9a747e4fSDavid du Colombier { 40*9a747e4fSDavid du Colombier io->ret = ret; 41*9a747e4fSDavid du Colombier if(ret < 0) 42*9a747e4fSDavid du Colombier rerrstr(io->err, sizeof io->err); 43*9a747e4fSDavid du Colombier sendp(io->c, io); 44*9a747e4fSDavid du Colombier } 45*9a747e4fSDavid du Colombier 46*9a747e4fSDavid du Colombier static void ioread2(Ioproc*); 47*9a747e4fSDavid du Colombier static long 48*9a747e4fSDavid du Colombier ioread(Ioproc *io, int fd, void *a, long n) 49*9a747e4fSDavid du Colombier { 50*9a747e4fSDavid du Colombier return t(io, ioread2, 3, fd, a, n); 51*9a747e4fSDavid du Colombier } 52*9a747e4fSDavid du Colombier static void 53*9a747e4fSDavid du Colombier ioread2(Ioproc *io) 54*9a747e4fSDavid du Colombier { 55*9a747e4fSDavid du Colombier t2(io, read(io->arg[0], (void*)io->arg[1], io->arg[2])); 56*9a747e4fSDavid du Colombier } 57*9a747e4fSDavid du Colombier 58*9a747e4fSDavid du Colombier static void iowrite2(Ioproc*); 59*9a747e4fSDavid du Colombier static long 60*9a747e4fSDavid du Colombier iowrite(Ioproc *io, int fd, void *a, long n) 61*9a747e4fSDavid du Colombier { 62*9a747e4fSDavid du Colombier return t(io, iowrite2, 3, fd, a, n); 63*9a747e4fSDavid du Colombier } 64*9a747e4fSDavid du Colombier static void 65*9a747e4fSDavid du Colombier iowrite2(Ioproc *io) 66*9a747e4fSDavid du Colombier { 67*9a747e4fSDavid du Colombier t2(io, write(io->arg[0], (void*)io->arg[1], io->arg[2])); 68*9a747e4fSDavid du Colombier } 69*9a747e4fSDavid du Colombier 70*9a747e4fSDavid du Colombier static void ioclose2(Ioproc*); 71*9a747e4fSDavid du Colombier static int 72*9a747e4fSDavid du Colombier ioclose(Ioproc *io, int fd) 73*9a747e4fSDavid du Colombier { 74*9a747e4fSDavid du Colombier return t(io, ioclose2, 1, fd); 75*9a747e4fSDavid du Colombier } 76*9a747e4fSDavid du Colombier static void 77*9a747e4fSDavid du Colombier ioclose2(Ioproc *io) 78*9a747e4fSDavid du Colombier { 79*9a747e4fSDavid du Colombier t2(io, close(io->arg[0])); 80*9a747e4fSDavid du Colombier } 81*9a747e4fSDavid du Colombier 82*9a747e4fSDavid du Colombier static void iodial2(Ioproc*); 83*9a747e4fSDavid du Colombier static int 84*9a747e4fSDavid du Colombier iodial(Ioproc *io, char *a, char *b, char *c, int *d, int e) 85*9a747e4fSDavid du Colombier { 86*9a747e4fSDavid du Colombier return t(io, iodial2, 5, a, b, c, d, e); 87*9a747e4fSDavid du Colombier } 88*9a747e4fSDavid du Colombier static void 89*9a747e4fSDavid du Colombier iodial2(Ioproc *io) 90*9a747e4fSDavid du Colombier { 91*9a747e4fSDavid du Colombier t2(io, tlsdial((char*)io->arg[0], (char*)io->arg[1], (char*)io->arg[2], (int*)io->arg[3], io->arg[4])); 92*9a747e4fSDavid du Colombier } 93*9a747e4fSDavid du Colombier 94*9a747e4fSDavid du Colombier static void ioopen2(Ioproc*); 95*9a747e4fSDavid du Colombier static int 96*9a747e4fSDavid du Colombier ioopen(Ioproc *io, char *path, int mode) 97*9a747e4fSDavid du Colombier { 98*9a747e4fSDavid du Colombier return t(io, ioopen2, 2, path, mode); 99*9a747e4fSDavid du Colombier } 100*9a747e4fSDavid du Colombier static void 101*9a747e4fSDavid du Colombier ioopen2(Ioproc *io) 102*9a747e4fSDavid du Colombier { 103*9a747e4fSDavid du Colombier t2(io, open((char*)io->arg[0], io->arg[1])); 104*9a747e4fSDavid du Colombier } 105*9a747e4fSDavid du Colombier 106*9a747e4fSDavid du Colombier static int 107*9a747e4fSDavid du Colombier ioprint(Ioproc *io, int fd, char *fmt, ...) 108*9a747e4fSDavid du Colombier { 109*9a747e4fSDavid du Colombier char buf[1024]; 110*9a747e4fSDavid du Colombier va_list arg; 111*9a747e4fSDavid du Colombier 112*9a747e4fSDavid du Colombier va_start(arg, fmt); 113*9a747e4fSDavid du Colombier vseprint(buf, buf+sizeof buf, fmt, arg); 114*9a747e4fSDavid du Colombier va_end(arg); 115*9a747e4fSDavid du Colombier return iowrite(io, fd, buf, strlen(buf)); 116*9a747e4fSDavid du Colombier } 117*9a747e4fSDavid du Colombier 118*9a747e4fSDavid du Colombier static void 119*9a747e4fSDavid du Colombier iointerrupt(Ioproc *io) 120*9a747e4fSDavid du Colombier { 121*9a747e4fSDavid du Colombier if(!io->inuse) 122*9a747e4fSDavid du Colombier return; 123*9a747e4fSDavid du Colombier postnote(PNPROC, io->pid, "interrupt"); 124*9a747e4fSDavid du Colombier } 125*9a747e4fSDavid du Colombier 126*9a747e4fSDavid du Colombier static void 127*9a747e4fSDavid du Colombier xioproc(void *a) 128*9a747e4fSDavid du Colombier { 129*9a747e4fSDavid du Colombier Ioproc *io; 130*9a747e4fSDavid du Colombier 131*9a747e4fSDavid du Colombier io = a; 132*9a747e4fSDavid du Colombier io->pid = getpid(); 133*9a747e4fSDavid du Colombier sendp(io->c, nil); 134*9a747e4fSDavid du Colombier while(recvp(io->c) == io) 135*9a747e4fSDavid du Colombier io->op(io); 136*9a747e4fSDavid du Colombier chanfree(io->c); 137*9a747e4fSDavid du Colombier free(io); 138*9a747e4fSDavid du Colombier } 139*9a747e4fSDavid du Colombier 140*9a747e4fSDavid du Colombier static int 141*9a747e4fSDavid du Colombier tlsdial(char *a, char *b, char *c, int *d, int usetls) 142*9a747e4fSDavid du Colombier { 143*9a747e4fSDavid du Colombier int fd, tfd; 144*9a747e4fSDavid du Colombier TLSconn conn; 145*9a747e4fSDavid du Colombier 146*9a747e4fSDavid du Colombier fd = dial(a, b, c, d); 147*9a747e4fSDavid du Colombier if(fd < 0) 148*9a747e4fSDavid du Colombier return -1; 149*9a747e4fSDavid du Colombier if(usetls == 0) 150*9a747e4fSDavid du Colombier return fd; 151*9a747e4fSDavid du Colombier 152*9a747e4fSDavid du Colombier memset(&conn, 0, sizeof conn); 153*9a747e4fSDavid du Colombier tfd = tlsClient(fd, &conn); 154*9a747e4fSDavid du Colombier if(tfd < 0){ 155*9a747e4fSDavid du Colombier print("tls %r\n"); 156*9a747e4fSDavid du Colombier close(fd); 157*9a747e4fSDavid du Colombier return -1; 158*9a747e4fSDavid du Colombier } 159*9a747e4fSDavid du Colombier /* BUG: check cert here? */ 160*9a747e4fSDavid du Colombier if(conn.cert) 161*9a747e4fSDavid du Colombier free(conn.cert); 162*9a747e4fSDavid du Colombier close(fd); 163*9a747e4fSDavid du Colombier return tfd; 164*9a747e4fSDavid du Colombier } 165*9a747e4fSDavid du Colombier 166*9a747e4fSDavid du Colombier Ioproc iofns = 167*9a747e4fSDavid du Colombier { 168*9a747e4fSDavid du Colombier ioread, 169*9a747e4fSDavid du Colombier iowrite, 170*9a747e4fSDavid du Colombier iodial, 171*9a747e4fSDavid du Colombier ioclose, 172*9a747e4fSDavid du Colombier ioopen, 173*9a747e4fSDavid du Colombier ioprint, 174*9a747e4fSDavid du Colombier iointerrupt, 175*9a747e4fSDavid du Colombier }; 176*9a747e4fSDavid du Colombier 177*9a747e4fSDavid du Colombier Ioproc *iofree; 178*9a747e4fSDavid du Colombier 179*9a747e4fSDavid du Colombier Ioproc* 180*9a747e4fSDavid du Colombier ioproc(void) 181*9a747e4fSDavid du Colombier { 182*9a747e4fSDavid du Colombier Ioproc *io; 183*9a747e4fSDavid du Colombier 184*9a747e4fSDavid du Colombier if((io = iofree) != nil){ 185*9a747e4fSDavid du Colombier iofree = io->next; 186*9a747e4fSDavid du Colombier return io; 187*9a747e4fSDavid du Colombier } 188*9a747e4fSDavid du Colombier io = emalloc(sizeof(*io)); 189*9a747e4fSDavid du Colombier *io = iofns; 190*9a747e4fSDavid du Colombier io->c = chancreate(sizeof(void*), 0); 191*9a747e4fSDavid du Colombier if(proccreate(xioproc, io, STACK) < 0) 192*9a747e4fSDavid du Colombier sysfatal("proccreate: %r"); 193*9a747e4fSDavid du Colombier recvp(io->c); 194*9a747e4fSDavid du Colombier return io; 195*9a747e4fSDavid du Colombier } 196*9a747e4fSDavid du Colombier 197*9a747e4fSDavid du Colombier void 198*9a747e4fSDavid du Colombier closeioproc(Ioproc *io) 199*9a747e4fSDavid du Colombier { 200*9a747e4fSDavid du Colombier io->next = iofree; 201*9a747e4fSDavid du Colombier iofree = io; 202*9a747e4fSDavid du Colombier } 203*9a747e4fSDavid du Colombier 204