Blame


1 7966faa9 2004-09-23 devnull #include <u.h>
2 7966faa9 2004-09-23 devnull #include <libc.h>
3 7966faa9 2004-09-23 devnull #include <thread.h>
4 7966faa9 2004-09-23 devnull #include "ioproc.h"
5 76193d7c 2003-09-30 devnull
6 76193d7c 2003-09-30 devnull enum
7 76193d7c 2003-09-30 devnull {
8 76193d7c 2003-09-30 devnull STACK = 8192,
9 76193d7c 2003-09-30 devnull };
10 76193d7c 2003-09-30 devnull
11 76193d7c 2003-09-30 devnull void
12 76193d7c 2003-09-30 devnull iointerrupt(Ioproc *io)
13 76193d7c 2003-09-30 devnull {
14 76193d7c 2003-09-30 devnull if(!io->inuse)
15 76193d7c 2003-09-30 devnull return;
16 76193d7c 2003-09-30 devnull threadint(io->tid);
17 76193d7c 2003-09-30 devnull }
18 76193d7c 2003-09-30 devnull
19 76193d7c 2003-09-30 devnull static void
20 76193d7c 2003-09-30 devnull xioproc(void *a)
21 76193d7c 2003-09-30 devnull {
22 76193d7c 2003-09-30 devnull Ioproc *io, *x;
23 76193d7c 2003-09-30 devnull io = a;
24 76193d7c 2003-09-30 devnull /*
25 76193d7c 2003-09-30 devnull * first recvp acquires the ioproc.
26 76193d7c 2003-09-30 devnull * second tells us that the data is ready.
27 76193d7c 2003-09-30 devnull */
28 76193d7c 2003-09-30 devnull for(;;){
29 76193d7c 2003-09-30 devnull while(recv(io->c, &x) == -1)
30 76193d7c 2003-09-30 devnull ;
31 76193d7c 2003-09-30 devnull if(x == 0) /* our cue to leave */
32 76193d7c 2003-09-30 devnull break;
33 76193d7c 2003-09-30 devnull assert(x == io);
34 76193d7c 2003-09-30 devnull
35 76193d7c 2003-09-30 devnull /* caller is now committed -- even if interrupted he'll return */
36 76193d7c 2003-09-30 devnull while(recv(io->creply, &x) == -1)
37 76193d7c 2003-09-30 devnull ;
38 76193d7c 2003-09-30 devnull if(x == 0) /* caller backed out */
39 76193d7c 2003-09-30 devnull continue;
40 76193d7c 2003-09-30 devnull assert(x == io);
41 76193d7c 2003-09-30 devnull
42 76193d7c 2003-09-30 devnull io->ret = io->op(&io->arg);
43 76193d7c 2003-09-30 devnull if(io->ret < 0)
44 76193d7c 2003-09-30 devnull rerrstr(io->err, sizeof io->err);
45 76193d7c 2003-09-30 devnull while(send(io->creply, &io) == -1)
46 76193d7c 2003-09-30 devnull ;
47 76193d7c 2003-09-30 devnull while(recv(io->creply, &x) == -1)
48 76193d7c 2003-09-30 devnull ;
49 76193d7c 2003-09-30 devnull }
50 76193d7c 2003-09-30 devnull }
51 76193d7c 2003-09-30 devnull
52 76193d7c 2003-09-30 devnull Ioproc*
53 76193d7c 2003-09-30 devnull ioproc(void)
54 76193d7c 2003-09-30 devnull {
55 76193d7c 2003-09-30 devnull Ioproc *io;
56 76193d7c 2003-09-30 devnull
57 76193d7c 2003-09-30 devnull io = mallocz(sizeof(*io), 1);
58 76193d7c 2003-09-30 devnull if(io == nil)
59 76193d7c 2003-09-30 devnull sysfatal("ioproc malloc: %r");
60 76193d7c 2003-09-30 devnull io->c = chancreate(sizeof(void*), 0);
61 76193d7c 2003-09-30 devnull io->creply = chancreate(sizeof(void*), 0);
62 76193d7c 2003-09-30 devnull io->tid = proccreate(xioproc, io, STACK);
63 76193d7c 2003-09-30 devnull return io;
64 76193d7c 2003-09-30 devnull }
65 76193d7c 2003-09-30 devnull
66 76193d7c 2003-09-30 devnull void
67 76193d7c 2003-09-30 devnull closeioproc(Ioproc *io)
68 76193d7c 2003-09-30 devnull {
69 76193d7c 2003-09-30 devnull if(io == nil)
70 76193d7c 2003-09-30 devnull return;
71 76193d7c 2003-09-30 devnull iointerrupt(io);
72 76193d7c 2003-09-30 devnull while(send(io->c, 0) == -1)
73 76193d7c 2003-09-30 devnull ;
74 76193d7c 2003-09-30 devnull chanfree(io->c);
75 76193d7c 2003-09-30 devnull chanfree(io->creply);
76 76193d7c 2003-09-30 devnull free(io);
77 76193d7c 2003-09-30 devnull }