1 #include "RPCPendingCalls.h" 2 #include <string.h> 3 4 extern bool conf_no_check_ip_xid; 5 6 extern void 7 PendingCallInit(struct PendingCall *call) 8 { 9 call->buffer=NULL; 10 } 11 12 extern void 13 PendingCallDestroy(struct PendingCall *call) 14 { 15 free (call->buffer); 16 } 17 18 extern void 19 RPCPendingCallsInit(struct RPCPendingCalls *calls) 20 { 21 SemaphorePoolInit(&calls->fPool); 22 23 calls->fFirst=NULL; 24 calls->fSem=create_sem(1,"RPCPendingCalls"); 25 set_sem_owner (calls->fSem,B_SYSTEM_TEAM); 26 } 27 28 extern void 29 RPCPendingCallsDestroy(struct RPCPendingCalls *calls) 30 { 31 delete_sem(calls->fSem); 32 33 while (calls->fFirst) 34 { 35 struct PendingCall *next=calls->fFirst->next; 36 37 SemaphorePoolPut (&calls->fPool,calls->fFirst->sem); 38 PendingCallDestroy (calls->fFirst); 39 free (calls->fFirst); 40 41 calls->fFirst=next; 42 } 43 44 SemaphorePoolDestroy (&calls->fPool); 45 } 46 47 extern struct PendingCall * 48 RPCPendingCallsAddPendingCall (struct RPCPendingCalls *calls, 49 int32 xid, const struct sockaddr_in *addr) 50 { 51 struct PendingCall *call=(struct PendingCall *)malloc(sizeof(struct PendingCall)); 52 PendingCallInit (call); 53 54 call->sem=SemaphorePoolGet(&calls->fPool); 55 56 memcpy(&call->addr,addr,sizeof(struct sockaddr_in)); 57 call->xid=xid; 58 59 while (acquire_sem (calls->fSem)==B_INTERRUPTED); 60 61 call->next=calls->fFirst; 62 calls->fFirst=call; 63 64 while (release_sem (calls->fSem)==B_INTERRUPTED); 65 66 return call; 67 } 68 69 extern struct PendingCall * 70 RPCPendingCallsFindAndRemovePendingCall (struct RPCPendingCalls *calls, 71 int32 xid, const struct sockaddr_in *addr) 72 { 73 struct PendingCall *last=NULL; 74 struct PendingCall *current; 75 76 while (acquire_sem (calls->fSem)==B_INTERRUPTED); 77 78 current=calls->fFirst; // mmu_man 79 80 while (current) 81 { 82 if (current->xid==xid) 83 { 84 if ((current->addr.sin_addr.s_addr==addr->sin_addr.s_addr)&& 85 (current->addr.sin_port==addr->sin_port) || conf_no_check_ip_xid) 86 { 87 if (last) 88 last->next=current->next; 89 else 90 calls->fFirst=current->next; 91 92 current->next=NULL; 93 94 while (release_sem (calls->fSem)==B_INTERRUPTED); 95 return current; 96 } 97 } 98 99 last=current; 100 current=current->next; 101 } 102 103 while (release_sem (calls->fSem)==B_INTERRUPTED); 104 105 return NULL; 106 } 107 108 extern void 109 SemaphorePoolInit(struct SemaphorePool *pool) 110 { 111 pool->fPool=NULL; 112 pool->fPoolCount=0; 113 pool->fPoolSize=0; 114 115 pool->fPoolSem=create_sem(1,"semaphore_pool_sem"); 116 set_sem_owner (pool->fPoolSem,B_SYSTEM_TEAM); 117 } 118 119 extern void 120 SemaphorePoolDestroy(struct SemaphorePool *pool) 121 { 122 int32 i; 123 124 for (i=0;i<pool->fPoolCount;i++) 125 delete_sem (pool->fPool[i]); 126 127 free (pool->fPool); 128 129 delete_sem (pool->fPoolSem); 130 } 131 132 extern sem_id 133 SemaphorePoolGet(struct SemaphorePool *pool) 134 { 135 sem_id sem; 136 137 while (acquire_sem(pool->fPoolSem)==B_INTERRUPTED) 138 { 139 } 140 141 if (pool->fPoolCount==0) 142 { 143 sem_id sem=create_sem (0,"pending_call"); 144 145 while (release_sem(pool->fPoolSem)==B_INTERRUPTED) 146 { 147 } 148 149 return sem; 150 } 151 152 sem=pool->fPool[pool->fPoolCount-1]; 153 pool->fPoolCount--; 154 155 while (release_sem(pool->fPoolSem)==B_INTERRUPTED) 156 { 157 } 158 159 return sem; 160 } 161 162 extern void 163 SemaphorePoolPut(struct SemaphorePool *pool, sem_id sem) 164 { 165 while (acquire_sem(pool->fPoolSem)==B_INTERRUPTED) 166 { 167 } 168 169 if (pool->fPoolCount+1>pool->fPoolSize) 170 { 171 pool->fPoolSize+=8; 172 pool->fPool=(sem_id *)realloc(pool->fPool,pool->fPoolSize*sizeof(sem_id)); 173 } 174 175 pool->fPool[pool->fPoolCount]=sem; 176 pool->fPoolCount++; 177 178 while (release_sem(pool->fPoolSem)==B_INTERRUPTED) 179 { 180 } 181 } 182 183