1 #include <u.h> 2 #include <libc.h> 3 #include <auth.h> 4 #include <fcall.h> 5 #include <thread.h> 6 #include <9p.h> 7 8 static void 9 increqref(void *v) 10 { 11 Req *r; 12 13 r = v; 14 if(r){ 15 if(chatty9p > 1) 16 fprint(2, "increfreq %p %ld\n", r, r->ref.ref); 17 incref(&r->ref); 18 } 19 } 20 21 Reqpool* 22 allocreqpool(void (*destroy)(Req*)) 23 { 24 Reqpool *f; 25 26 f = emalloc9p(sizeof *f); 27 f->map = allocmap(increqref); 28 f->destroy = destroy; 29 return f; 30 } 31 32 void 33 freereqpool(Reqpool *p) 34 { 35 freemap(p->map, (void(*)(void*))p->destroy); 36 free(p); 37 } 38 39 Req* 40 allocreq(Reqpool *pool, ulong tag) 41 { 42 Req *r; 43 44 r = emalloc9p(sizeof *r); 45 r->tag = tag; 46 r->pool = pool; 47 48 increqref(r); 49 increqref(r); 50 if(caninsertkey(pool->map, tag, r) == 0){ 51 closereq(r); 52 return nil; 53 } 54 55 return r; 56 } 57 58 Req* 59 lookupreq(Reqpool *pool, ulong tag) 60 { 61 if(chatty9p > 1) 62 fprint(2, "lookupreq %lud\n", tag); 63 return lookupkey(pool->map, tag); 64 } 65 66 void 67 closereq(Req *r) 68 { 69 int i; 70 71 if(r == nil) 72 return; 73 74 if(chatty9p > 1) 75 fprint(2, "closereq %p %ld\n", r, r->ref.ref); 76 77 if(decref(&r->ref) == 0){ 78 if(r->fid) 79 closefid(r->fid); 80 if(r->newfid) 81 closefid(r->newfid); 82 if(r->afid) 83 closefid(r->afid); 84 if(r->oldreq) 85 closereq(r->oldreq); 86 for(i=0; i<r->nflush; i++) 87 respond(r->flush[i], nil); 88 free(r->flush); 89 switch(r->ifcall.type){ 90 case Tstat: 91 free(r->ofcall.stat); 92 free(r->d.name); 93 free(r->d.uid); 94 free(r->d.gid); 95 free(r->d.muid); 96 break; 97 } 98 if(r->pool->destroy) 99 r->pool->destroy(r); 100 free(r->buf); 101 free(r->rbuf); 102 free(r); 103 } 104 } 105 106 Req* 107 removereq(Reqpool *pool, ulong tag) 108 { 109 if(chatty9p > 1) 110 fprint(2, "removereq %lud\n", tag); 111 return deletekey(pool->map, tag); 112 } 113