Changeset 2552
- Timestamp:
- Jul 30, 2007, 3:27:52 PM (15 years ago)
- Location:
- trunk/libtransmission
- Files:
-
- 13 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/libtransmission/choking.c
r2544 r2552 36 36 struct tr_choking_s 37 37 { 38 tr_lock_t 38 tr_lock_t * lock; 39 39 tr_handle_t * h; 40 40 int slots; … … 48 48 c->h = h; 49 49 c->slots = 4242; 50 tr_lockInit( &c->lock);50 c->lock = tr_lockNew( ); 51 51 52 52 return c; … … 55 55 void tr_chokingSetLimit( tr_choking_t * c, int limit ) 56 56 { 57 tr_lockLock( &c->lock );57 tr_lockLock( c->lock ); 58 58 if( limit < 0 ) 59 59 c->slots = 4242; … … 66 66 100 KB/s -> 14 * 7.14 KB/s */ 67 67 c->slots = lrintf( sqrt( 2 * limit ) ); 68 tr_lockUnlock( &c->lock );68 tr_lockUnlock( c->lock ); 69 69 } 70 70 … … 138 138 uint64_t now = tr_date(); 139 139 140 tr_lockLock( &c->lock );140 tr_lockLock( c->lock ); 141 141 142 142 /* Lock all torrents and get the total number of peers */ … … 311 311 tr_torrentWriterUnlock( tor ); 312 312 313 tr_lockUnlock( &c->lock );313 tr_lockUnlock( c->lock ); 314 314 } 315 315 316 316 void tr_chokingClose( tr_choking_t * c ) 317 317 { 318 tr_lock Close( &c->lock );318 tr_lockFree( c->lock ); 319 319 tr_free( c ); 320 320 } -
trunk/libtransmission/fdlimit.c
r2544 r2552 64 64 typedef struct tr_fd_s 65 65 { 66 tr_lock_t 67 tr_cond_t 66 tr_lock_t * lock; 67 tr_cond_t * cond; 68 68 69 69 int reserved; … … 101 101 102 102 /* Init lock and cond */ 103 tr_lockInit( &gFd->lock);104 tr_condInit( &gFd->cond);103 gFd->lock = tr_lockNew( ); 104 gFd->cond = tr_condNew( ); 105 105 106 106 /* Detect the maximum number of open files or sockets */ … … 144 144 uint64_t date; 145 145 146 tr_lockLock( &gFd->lock );146 tr_lockLock( gFd->lock ); 147 147 148 148 /* Is it already open? */ … … 159 159 /* File is being closed by another thread, wait until 160 160 * it's done before we reopen it */ 161 tr_condWait( &gFd->cond, &gFd->lock );161 tr_condWait( gFd->cond, gFd->lock ); 162 162 i = -1; 163 163 continue; … … 210 210 211 211 /* All used! Wait a bit and try again */ 212 tr_condWait( &gFd->cond, &gFd->lock );212 tr_condWait( gFd->cond, gFd->lock ); 213 213 } 214 214 … … 216 216 if( ( ret = OpenFile( winner, folder, name, write ) ) ) 217 217 { 218 tr_lockUnlock( &gFd->lock );218 tr_lockUnlock( gFd->lock ); 219 219 return ret; 220 220 } … … 226 226 gFd->open[winner].status = STATUS_USED; 227 227 gFd->open[winner].date = tr_date(); 228 tr_lockUnlock( &gFd->lock );228 tr_lockUnlock( gFd->lock ); 229 229 230 230 return gFd->open[winner].file; … … 237 237 { 238 238 int i; 239 tr_lockLock( &gFd->lock );239 tr_lockLock( gFd->lock ); 240 240 241 241 for( i = 0; i < TR_MAX_OPEN_FILES; i++ ) … … 248 248 } 249 249 250 tr_condSignal( &gFd->cond );251 tr_lockUnlock( &gFd->lock );250 tr_condSignal( gFd->cond ); 251 tr_lockUnlock( gFd->lock ); 252 252 } 253 253 … … 259 259 int i; 260 260 261 tr_lockLock( &gFd->lock );261 tr_lockLock( gFd->lock ); 262 262 263 263 for( i = 0; i < TR_MAX_OPEN_FILES; i++ ) … … 274 274 } 275 275 276 tr_lockUnlock( &gFd->lock );276 tr_lockUnlock( gFd->lock ); 277 277 } 278 278 … … 334 334 int s = -1; 335 335 336 tr_lockLock( &gFd->lock );336 tr_lockLock( gFd->lock ); 337 337 338 338 if( priority && gFd->reserved >= TR_RESERVED_FDS ) … … 351 351 gFd->normal++; 352 352 } 353 tr_lockUnlock( &gFd->lock );353 tr_lockUnlock( gFd->lock ); 354 354 355 355 return s; … … 362 362 struct sockaddr_in sock; 363 363 364 tr_lockLock( &gFd->lock );364 tr_lockLock( gFd->lock ); 365 365 if( gFd->normal < gFd->normalMax ) 366 366 { … … 381 381 gFd->normal++; 382 382 } 383 tr_lockUnlock( &gFd->lock );383 tr_lockUnlock( gFd->lock ); 384 384 385 385 return s; … … 391 391 void tr_fdSocketClose( int s ) 392 392 { 393 tr_lockLock( &gFd->lock );393 tr_lockLock( gFd->lock ); 394 394 #ifdef BEOS_NETSERVER 395 395 closesocket( s ); … … 401 401 else 402 402 gFd->normal--; 403 tr_lockUnlock( &gFd->lock );403 tr_lockUnlock( gFd->lock ); 404 404 } 405 405 … … 409 409 void tr_fdClose() 410 410 { 411 tr_lock Close( &gFd->lock );412 tr_cond Close( &gFd->cond );411 tr_lockFree( gFd->lock ); 412 tr_condFree( gFd->cond ); 413 413 free( gFd ); 414 414 } … … 505 505 while( file->status & STATUS_CLOSING ) 506 506 { 507 tr_condWait( &gFd->cond, &gFd->lock );507 tr_condWait( gFd->cond, gFd->lock ); 508 508 } 509 509 if( file->status & STATUS_INVALID ) … … 519 519 tr_dbg( "Closing %s in %s (%d)", file->name, file->folder, file->write ); 520 520 file->status = STATUS_CLOSING; 521 tr_lockUnlock( &gFd->lock );521 tr_lockUnlock( gFd->lock ); 522 522 close( file->file ); 523 tr_lockLock( &gFd->lock );523 tr_lockLock( gFd->lock ); 524 524 file->status = STATUS_INVALID; 525 tr_condSignal( &gFd->cond );526 } 527 525 tr_condSignal( gFd->cond ); 526 } 527 -
trunk/libtransmission/internal.h
r2549 r2552 194 194 run_status_t runStatus; 195 195 cp_status_t cpStatus; 196 tr_thread_t 197 tr_rwlock_t 196 tr_thread_t * thread; 197 tr_rwlock_t * lock; 198 198 199 199 tr_tracker_t * tracker; -
trunk/libtransmission/list.h
r2310 r2552 24 24 tr_list_t* tr_list_prepend ( tr_list_t*, void * data ); 25 25 tr_list_t* tr_list_remove_data ( tr_list_t*, const void * data ); 26 tr_list_t* tr_list_pop ( tr_list_t*, void ** setme );27 26 28 27 typedef int (*TrListCompareFunc)(const void * a, const void * b); -
trunk/libtransmission/makemeta.c
r2544 r2552 408 408 static tr_metainfo_builder_t * queue = NULL; 409 409 410 static int workerIsRunning = 0; 411 412 static tr_thread_t workerThread; 410 static tr_thread_t * workerThread = NULL; 413 411 414 412 static tr_lock_t* getQueueLock( tr_handle_t * h ) … … 417 415 418 416 tr_sharedLock( h->shared ); 419 if( lock == NULL ) 420 { 421 lock = tr_new0( tr_lock_t, 1 ); 422 tr_lockInit( lock ); 423 } 417 if( !lock ) 418 lock = tr_lockNew( ); 424 419 tr_sharedUnlock( h->shared ); 425 420 … … 451 446 } 452 447 453 worker IsRunning = 0;448 workerThread = NULL; 454 449 } 455 450 … … 481 476 builder->nextBuilder = queue; 482 477 queue = builder; 483 if( !workerIsRunning ) { 484 workerIsRunning = 1; 485 tr_threadCreate( &workerThread, workerFunc, builder->handle, "makeMeta" ); 486 } 478 if( !workerThread ) 479 workerThread = tr_threadNew( workerFunc, builder->handle, "makeMeta" ); 487 480 tr_lockUnlock( lock ); 488 481 } -
trunk/libtransmission/net.c
r2544 r2552 57 57 } 58 58 59 static tr_thread_t resolveThread;60 static tr_lock_t resolveLock;61 static tr_cond_t resolveCond;62 static volatile int resolveDie;59 static tr_thread_t * resolveThread; 60 static tr_lock_t * resolveLock; 61 static tr_cond_t * resolveCond; 62 static volatile int resolveDie; 63 63 static tr_resolve_t * resolveQueue; 64 64 … … 86 86 resolveDie = 0; 87 87 resolveQueue = NULL; 88 tr_lockInit( &resolveLock);89 tr_condInit( &resolveCond);90 tr_threadCreate( &resolveThread,resolveFunc, NULL, "resolve" );88 resolveLock = tr_lockNew( ); 89 resolveCond = tr_condNew( ); 90 resolveThread = tr_threadNew( resolveFunc, NULL, "resolve" ); 91 91 } 92 92 … … 100 100 void tr_netResolveThreadClose() 101 101 { 102 tr_lockLock( &resolveLock );102 tr_lockLock( resolveLock ); 103 103 resolveDie = 1; 104 tr_lockUnlock( &resolveLock );105 tr_condSignal( &resolveCond );104 tr_lockUnlock( resolveLock ); 105 tr_condSignal( resolveCond ); 106 106 tr_wait( 200 ); 107 107 } … … 114 114 tr_resolve_t * tr_netResolveInit( const char * address ) 115 115 { 116 tr_resolve_t * r; 117 118 r = malloc( sizeof( tr_resolve_t ) ); 116 tr_resolve_t * r = tr_new0( tr_resolve_t, 1 ); 119 117 r->status = TR_NET_WAIT; 120 118 r->address = strdup( address ); … … 122 120 r->next = NULL; 123 121 124 tr_lockLock( &resolveLock );122 tr_lockLock( resolveLock ); 125 123 if( !resolveQueue ) 126 124 { … … 133 131 iter->next = r; 134 132 } 135 tr_lockUnlock( &resolveLock );136 tr_condSignal( &resolveCond );133 tr_lockUnlock( resolveLock ); 134 tr_condSignal( resolveCond ); 137 135 138 136 return r; … … 148 146 tr_tristate_t ret; 149 147 150 tr_lockLock( &resolveLock );148 tr_lockLock( resolveLock ); 151 149 ret = r->status; 152 150 if( ret == TR_NET_OK ) … … 154 152 *addr = r->addr; 155 153 } 156 tr_lockUnlock( &resolveLock );154 tr_lockUnlock( resolveLock ); 157 155 158 156 return ret; … … 197 195 struct hostent * host; 198 196 199 tr_lockLock( &resolveLock );197 tr_lockLock( resolveLock ); 200 198 201 199 while( !resolveDie ) … … 203 201 if( !( r = resolveQueue ) ) 204 202 { 205 tr_condWait( &resolveCond, &resolveLock );203 tr_condWait( resolveCond, resolveLock ); 206 204 continue; 207 205 } 208 206 209 207 /* Blocking resolution */ 210 tr_lockUnlock( &resolveLock );208 tr_lockUnlock( resolveLock ); 211 209 host = gethostbyname( r->address ); 212 tr_lockLock( &resolveLock );210 tr_lockLock( resolveLock ); 213 211 214 212 if( host ) … … 227 225 228 226 /* Clean up */ 229 tr_lockUnlock( &resolveLock ); 230 tr_lockClose( &resolveLock ); 227 tr_lockUnlock( resolveLock ); 228 tr_lockFree( resolveLock ); 229 resolveLock = NULL; 231 230 while( ( r = resolveQueue ) ) 232 231 { -
trunk/libtransmission/net.h
r2343 r2552 35 35 void tr_netResolveThreadInit(); 36 36 void tr_netResolveThreadClose(); 37 tr_resolve_t * tr_netResolveInit( const char * );37 tr_resolve_t * tr_netResolveInit( const char * address ); 38 38 tr_tristate_t tr_netResolvePulse( tr_resolve_t *, struct in_addr * ); 39 39 void tr_netResolveClose( tr_resolve_t * ); -
trunk/libtransmission/platform.c
r2544 r2552 31 31 #include <fs_info.h> 32 32 #include <FindDirectory.h> 33 #endif 33 #include <kernel/OS.h> 34 #define BEOS_MAX_THREADS 256 35 #else 36 #include <pthread.h> 37 #endif 38 34 39 #include <sys/types.h> 35 40 #include <dirent.h> … … 38 43 39 44 #include "transmission.h" 45 #include "utils.h" 46 47 /*** 48 **** THREADS 49 ***/ 50 51 struct tr_thread_s 52 { 53 void (* func ) ( void * ); 54 void * arg; 55 char * name; 56 57 #ifdef SYS_BEOS 58 thread_id thread; 59 #else 60 pthread_t thread; 61 #endif 62 63 }; 64 65 static void 66 ThreadFunc( void * _t ) 67 { 68 tr_thread_t * t = _t; 69 char* name = tr_strdup( t->name ); 70 71 #ifdef SYS_BEOS 72 /* This is required because on BeOS, SIGINT is sent to each thread, 73 which kills them not nicely */ 74 signal( SIGINT, SIG_IGN ); 75 #endif 76 77 tr_dbg( "Thread '%s' started", name ); 78 t->func( t->arg ); 79 tr_dbg( "Thread '%s' exited", name ); 80 tr_free( name ); 81 } 82 83 tr_thread_t * 84 tr_threadNew( void (*func)(void *), 85 void * arg, 86 const char * name ) 87 { 88 tr_thread_t * t = tr_new0( tr_thread_t, 1 ); 89 t->func = func; 90 t->arg = arg; 91 t->name = tr_strdup( name ); 92 93 #ifdef SYS_BEOS 94 t->thread = spawn_thread( (void*)ThreadFunc, name, B_NORMAL_PRIORITY, t ); 95 resume_thread( t->thread ); 96 #else 97 pthread_create( &t->thread, NULL, (void * (*) (void *)) ThreadFunc, t ); 98 #endif 99 100 return t; 101 } 102 103 void 104 tr_threadJoin( tr_thread_t * t ) 105 { 106 if( t != NULL ) 107 { 108 #ifdef SYS_BEOS 109 long exit; 110 wait_for_thread( t->thread, &exit ); 111 #else 112 pthread_join( t->thread, NULL ); 113 #endif 114 115 tr_dbg( "Thread '%s' joined", t->name ); 116 tr_free( t->name ); 117 t->name = NULL; 118 t->func = NULL; 119 tr_free( t ); 120 } 121 } 122 123 /*** 124 **** LOCKS 125 ***/ 126 127 struct tr_lock_s 128 { 129 #ifdef SYS_BEOS 130 sem_id lock; 131 #else 132 pthread_mutex_t lock; 133 #endif 134 }; 135 136 tr_lock_t* 137 tr_lockNew( void ) 138 { 139 tr_lock_t * l = tr_new0( tr_lock_t, 1 ); 140 141 #ifdef SYS_BEOS 142 l->lock = create_sem( 1, "" ); 143 #else 144 pthread_mutex_init( &l->lock, NULL ); 145 #endif 146 147 return l; 148 } 149 150 void 151 tr_lockFree( tr_lock_t * l ) 152 { 153 #ifdef SYS_BEOS 154 delete_sem( l->lock ); 155 #else 156 pthread_mutex_destroy( &l->lock ); 157 #endif 158 tr_free( l ); 159 } 160 161 int 162 tr_lockTryLock( tr_lock_t * l ) 163 { 164 #ifdef SYS_BEOS 165 return acquire_sem_etc( l->lock, 1, B_RELATIVE_TIMEOUT, 0 ); 166 #else 167 /* success on zero! */ 168 return pthread_mutex_trylock( &l->lock ); 169 #endif 170 } 171 172 void 173 tr_lockLock( tr_lock_t * l ) 174 { 175 #ifdef SYS_BEOS 176 acquire_sem( l->lock ); 177 #else 178 pthread_mutex_lock( &l->lock ); 179 #endif 180 } 181 182 void 183 tr_lockUnlock( tr_lock_t * l ) 184 { 185 #ifdef SYS_BEOS 186 release_sem( l->lock ); 187 #else 188 pthread_mutex_unlock( &l->lock ); 189 #endif 190 } 191 192 /*** 193 **** RW LOCK 194 ***/ 195 196 struct tr_rwlock_s 197 { 198 tr_lock_t * lock; 199 tr_cond_t * readCond; 200 tr_cond_t * writeCond; 201 size_t readCount; 202 size_t wantToRead; 203 size_t wantToWrite; 204 int haveWriter; 205 }; 206 207 static void 208 tr_rwSignal( tr_rwlock_t * rw ) 209 { 210 if ( rw->wantToWrite ) 211 tr_condSignal( rw->writeCond ); 212 else if ( rw->wantToRead ) 213 tr_condBroadcast( rw->readCond ); 214 } 215 216 tr_rwlock_t* 217 tr_rwNew ( void ) 218 { 219 tr_rwlock_t * rw = tr_new0( tr_rwlock_t, 1 ); 220 rw->lock = tr_lockNew( ); 221 rw->readCond = tr_condNew( ); 222 rw->writeCond = tr_condNew( ); 223 return rw; 224 } 225 226 void 227 tr_rwReaderLock( tr_rwlock_t * rw ) 228 { 229 tr_lockLock( rw->lock ); 230 rw->wantToRead++; 231 while( rw->haveWriter || rw->wantToWrite ) 232 tr_condWait( rw->readCond, rw->lock ); 233 rw->wantToRead--; 234 rw->readCount++; 235 tr_lockUnlock( rw->lock ); 236 } 237 238 int 239 tr_rwReaderTrylock( tr_rwlock_t * rw ) 240 { 241 int ret = FALSE; 242 tr_lockLock( rw->lock ); 243 if ( !rw->haveWriter && !rw->wantToWrite ) { 244 rw->readCount++; 245 ret = TRUE; 246 } 247 tr_lockUnlock( rw->lock ); 248 return ret; 249 250 } 251 252 void 253 tr_rwReaderUnlock( tr_rwlock_t * rw ) 254 { 255 tr_lockLock( rw->lock ); 256 --rw->readCount; 257 if( !rw->readCount ) 258 tr_rwSignal( rw ); 259 tr_lockUnlock( rw->lock ); 260 } 261 262 void 263 tr_rwWriterLock( tr_rwlock_t * rw ) 264 { 265 tr_lockLock( rw->lock ); 266 rw->wantToWrite++; 267 while( rw->haveWriter || rw->readCount ) 268 tr_condWait( rw->writeCond, rw->lock ); 269 rw->wantToWrite--; 270 rw->haveWriter = TRUE; 271 tr_lockUnlock( rw->lock ); 272 } 273 274 int 275 tr_rwWriterTrylock( tr_rwlock_t * rw ) 276 { 277 int ret = FALSE; 278 tr_lockLock( rw->lock ); 279 if( !rw->haveWriter && !rw->readCount ) 280 ret = rw->haveWriter = TRUE; 281 tr_lockUnlock( rw->lock ); 282 return ret; 283 } 284 void 285 tr_rwWriterUnlock( tr_rwlock_t * rw ) 286 { 287 tr_lockLock( rw->lock ); 288 rw->haveWriter = FALSE; 289 tr_rwSignal( rw ); 290 tr_lockUnlock( rw->lock ); 291 } 292 293 void 294 tr_rwFree( tr_rwlock_t * rw ) 295 { 296 tr_condFree( rw->writeCond ); 297 tr_condFree( rw->readCond ); 298 tr_lockFree( rw->lock ); 299 tr_free( rw ); 300 } 301 302 /*** 303 **** COND 304 ***/ 305 306 struct tr_cond_s 307 { 308 #ifdef SYS_BEOS 309 sem_id sem; 310 thread_id theads[BEOS_MAX_THREADS]; 311 int start, end; 312 #else 313 pthread_cond_t cond; 314 #endif 315 }; 316 317 tr_cond_t* 318 tr_condNew( void ) 319 { 320 tr_cond_t * c = tr_new0( tr_cond_t, 1 ); 321 #ifdef SYS_BEOS 322 c->sem = create_sem( 1, "" ); 323 c->start = 0; 324 c->end = 0; 325 #else 326 pthread_cond_init( &c->cond, NULL ); 327 #endif 328 return c; 329 } 330 331 void tr_condWait( tr_cond_t * c, tr_lock_t * l ) 332 { 333 #ifdef SYS_BEOS 334 /* Keep track of that thread */ 335 acquire_sem( c->sem ); 336 c->threads[c->end] = find_thread( NULL ); 337 c->end = ( c->end + 1 ) % BEOS_MAX_THREADS; 338 assert( c->end != c->start ); /* We hit BEOS_MAX_THREADS, arggh */ 339 release_sem( c->sem ); 340 341 release_sem( *l ); 342 suspend_thread( find_thread( NULL ) ); /* Wait for signal */ 343 acquire_sem( *l ); 344 #else 345 pthread_cond_wait( &c->cond, &l->lock ); 346 #endif 347 } 348 349 #ifdef SYS_BEOS 350 static int condTrySignal( tr_cond_t * c ) 351 { 352 if( c->start == c->end ) 353 return 1; 354 355 for( ;; ) 356 { 357 thread_info info; 358 get_thread_info( c->threads[c->start], &info ); 359 if( info.state == B_THREAD_SUSPENDED ) 360 { 361 resume_thread( c->threads[c->start] ); 362 c->start = ( c->start + 1 ) % BEOS_MAX_THREADS; 363 break; 364 } 365 /* The thread is not suspended yet, which can happen since 366 * tr_condWait does not atomically suspends after releasing 367 * the semaphore. Wait a bit and try again. */ 368 snooze( 5000 ); 369 } 370 return 0; 371 } 372 #endif 373 void tr_condSignal( tr_cond_t * c ) 374 { 375 #ifdef SYS_BEOS 376 acquire_sem( c->sem ); 377 condTrySignal( c ); 378 release_sem( c->sem ); 379 #else 380 pthread_cond_signal( &c->cond ); 381 #endif 382 } 383 void tr_condBroadcast( tr_cond_t * c ) 384 { 385 #ifdef SYS_BEOS 386 acquire_sem( c->sem ); 387 while( !condTrySignal( c ) ); 388 release_sem( c->sem ); 389 #else 390 pthread_cond_broadcast( &c->cond ); 391 #endif 392 } 393 394 void 395 tr_condFree( tr_cond_t * c ) 396 { 397 #ifdef SYS_BEOS 398 delete_sem( c->sem ); 399 #else 400 pthread_cond_destroy( &c->cond ); 401 #endif 402 tr_free( c ); 403 } 404 405 406 /*** 407 **** PATHS 408 ***/ 40 409 41 410 #if !defined( SYS_BEOS ) && !defined( __AMIGAOS4__ ) … … 205 574 } 206 575 207 static void ThreadFunc( void * _t ) 208 { 209 tr_thread_t * t = _t; 210 char* name = tr_strdup( t->name ); 211 212 #ifdef SYS_BEOS 213 /* This is required because on BeOS, SIGINT is sent to each thread, 214 which kills them not nicely */ 215 signal( SIGINT, SIG_IGN ); 216 #endif 217 218 tr_dbg( "Thread '%s' started", name ); 219 t->func( t->arg ); 220 tr_dbg( "Thread '%s' exited", name ); 221 tr_free( name ); 222 } 223 224 void tr_threadCreate( tr_thread_t * t, 225 void (*func)(void *), void * arg, 226 const char * name ) 227 { 228 t->func = func; 229 t->arg = arg; 230 t->name = tr_strdup( name ); 231 #ifdef SYS_BEOS 232 t->thread = spawn_thread( (void *) ThreadFunc, name, 233 B_NORMAL_PRIORITY, t ); 234 resume_thread( t->thread ); 235 #else 236 pthread_create( &t->thread, NULL, (void * (*) (void *)) ThreadFunc, t ); 237 #endif 238 } 239 240 const tr_thread_t THREAD_EMPTY = { NULL, NULL, NULL, 0 }; 241 242 void tr_threadJoin( tr_thread_t * t ) 243 { 244 if( t->func != NULL ) 245 { 246 #ifdef SYS_BEOS 247 long exit; 248 wait_for_thread( t->thread, &exit ); 249 #else 250 pthread_join( t->thread, NULL ); 251 #endif 252 tr_dbg( "Thread '%s' joined", t->name ); 253 tr_free( t->name ); 254 t->name = NULL; 255 t->func = NULL; 256 } 257 } 258 259 void tr_lockInit( tr_lock_t * l ) 260 { 261 #ifdef SYS_BEOS 262 *l = create_sem( 1, "" ); 263 #else 264 pthread_mutex_init( l, NULL ); 265 #endif 266 } 267 268 void tr_lockClose( tr_lock_t * l ) 269 { 270 #ifdef SYS_BEOS 271 delete_sem( *l ); 272 #else 273 pthread_mutex_destroy( l ); 274 #endif 275 } 276 277 int tr_lockTryLock( tr_lock_t * l ) 278 { 279 #ifdef SYS_BEOS 280 return acquire_sem_etc( *l, 1, B_RELATIVE_TIMEOUT, 0 ); 281 #else 282 /* success on zero! */ 283 return pthread_mutex_trylock( l ); 284 #endif 285 } 286 287 void tr_lockLock( tr_lock_t * l ) 288 { 289 #ifdef SYS_BEOS 290 acquire_sem( *l ); 291 #else 292 pthread_mutex_lock( l ); 293 #endif 294 } 295 296 void tr_lockUnlock( tr_lock_t * l ) 297 { 298 #ifdef SYS_BEOS 299 release_sem( *l ); 300 #else 301 pthread_mutex_unlock( l ); 302 #endif 303 } 304 305 306 void tr_condInit( tr_cond_t * c ) 307 { 308 #ifdef SYS_BEOS 309 c->sem = create_sem( 1, "" ); 310 c->start = 0; 311 c->end = 0; 312 #else 313 pthread_cond_init( c, NULL ); 314 #endif 315 } 316 317 void tr_condWait( tr_cond_t * c, tr_lock_t * l ) 318 { 319 #ifdef SYS_BEOS 320 /* Keep track of that thread */ 321 acquire_sem( c->sem ); 322 c->threads[c->end] = find_thread( NULL ); 323 c->end = ( c->end + 1 ) % BEOS_MAX_THREADS; 324 assert( c->end != c->start ); /* We hit BEOS_MAX_THREADS, arggh */ 325 release_sem( c->sem ); 326 327 release_sem( *l ); 328 suspend_thread( find_thread( NULL ) ); /* Wait for signal */ 329 acquire_sem( *l ); 330 #else 331 pthread_cond_wait( c, l ); 332 #endif 333 } 334 335 #ifdef SYS_BEOS 336 static int condTrySignal( tr_cond_t * c ) 337 { 338 if( c->start == c->end ) 339 return 1; 340 341 for( ;; ) 342 { 343 thread_info info; 344 get_thread_info( c->threads[c->start], &info ); 345 if( info.state == B_THREAD_SUSPENDED ) 346 { 347 resume_thread( c->threads[c->start] ); 348 c->start = ( c->start + 1 ) % BEOS_MAX_THREADS; 349 break; 350 } 351 /* The thread is not suspended yet, which can happen since 352 * tr_condWait does not atomically suspends after releasing 353 * the semaphore. Wait a bit and try again. */ 354 snooze( 5000 ); 355 } 356 return 0; 357 } 358 #endif 359 void tr_condSignal( tr_cond_t * c ) 360 { 361 #ifdef SYS_BEOS 362 acquire_sem( c->sem ); 363 condTrySignal( c ); 364 release_sem( c->sem ); 365 #else 366 pthread_cond_signal( c ); 367 #endif 368 } 369 void tr_condBroadcast( tr_cond_t * c ) 370 { 371 #ifdef SYS_BEOS 372 acquire_sem( c->sem ); 373 while( !condTrySignal( c ) ); 374 release_sem( c->sem ); 375 #else 376 pthread_cond_broadcast( c ); 377 #endif 378 } 379 380 void tr_condClose( tr_cond_t * c ) 381 { 382 #ifdef SYS_BEOS 383 delete_sem( c->sem ); 384 #else 385 pthread_cond_destroy( c ); 386 #endif 387 } 388 389 390 #if defined( BSD ) 576 /*** 577 **** SOCKETS 578 ***/ 579 580 #ifdef BSD 391 581 392 582 #include <sys/types.h> … … 760 950 761 951 #endif 762 763 /***764 ****765 ***/766 767 static void768 tr_rwSignal( tr_rwlock_t * rw )769 {770 if ( rw->wantToWrite )771 tr_condSignal( &rw->writeCond );772 else if ( rw->wantToRead )773 tr_condBroadcast( &rw->readCond );774 }775 776 void777 tr_rwInit ( tr_rwlock_t * rw )778 {779 memset( rw, 0, sizeof(tr_rwlock_t) );780 tr_lockInit( &rw->lock );781 tr_condInit( &rw->readCond );782 tr_condInit( &rw->writeCond );783 }784 785 void786 tr_rwReaderLock( tr_rwlock_t * rw )787 {788 tr_lockLock( &rw->lock );789 rw->wantToRead++;790 while( rw->haveWriter || rw->wantToWrite )791 tr_condWait( &rw->readCond, &rw->lock );792 rw->wantToRead--;793 rw->readCount++;794 tr_lockUnlock( &rw->lock );795 }796 797 int798 tr_rwReaderTrylock( tr_rwlock_t * rw )799 {800 int ret = FALSE;801 tr_lockLock( &rw->lock );802 if ( !rw->haveWriter && !rw->wantToWrite ) {803 rw->readCount++;804 ret = TRUE;805 }806 tr_lockUnlock( &rw->lock );807 return ret;808 809 }810 811 void812 tr_rwReaderUnlock( tr_rwlock_t * rw )813 {814 tr_lockLock( &rw->lock );815 --rw->readCount;816 if( !rw->readCount )817 tr_rwSignal( rw );818 tr_lockUnlock( &rw->lock );819 }820 821 void822 tr_rwWriterLock( tr_rwlock_t * rw )823 {824 tr_lockLock( &rw->lock );825 rw->wantToWrite++;826 while( rw->haveWriter || rw->readCount )827 tr_condWait( &rw->writeCond, &rw->lock );828 rw->wantToWrite--;829 rw->haveWriter = TRUE;830 tr_lockUnlock( &rw->lock );831 }832 833 int834 tr_rwWriterTrylock( tr_rwlock_t * rw )835 {836 int ret = FALSE;837 tr_lockLock( &rw->lock );838 if( !rw->haveWriter && !rw->readCount )839 ret = rw->haveWriter = TRUE;840 tr_lockUnlock( &rw->lock );841 return ret;842 }843 void844 tr_rwWriterUnlock( tr_rwlock_t * rw )845 {846 tr_lockLock( &rw->lock );847 rw->haveWriter = FALSE;848 tr_rwSignal( rw );849 tr_lockUnlock( &rw->lock );850 }851 852 void853 tr_rwClose( tr_rwlock_t * rw )854 {855 tr_condClose( &rw->writeCond );856 tr_condClose( &rw->readCond );857 tr_lockClose( &rw->lock );858 } -
trunk/libtransmission/platform.h
r2323 r2552 23 23 *****************************************************************************/ 24 24 #ifndef TR_PLATFORM_H 25 #define TR_PLATFORM_H 125 #define TR_PLATFORM_H 26 26 27 #ifdef SYS_BEOS 28 #include <kernel/OS.h> 29 #define BEOS_MAX_THREADS 256 30 typedef thread_id tr_thread_id_t; 31 typedef sem_id tr_lock_t; 32 typedef struct 33 { 34 sem_id sem; 35 thread_id threads[BEOS_MAX_THREADS]; 36 int start; 37 int end; 38 } tr_cond_t; 39 #else 40 #include <pthread.h> 41 typedef pthread_t tr_thread_id_t; 42 typedef pthread_mutex_t tr_lock_t; 43 typedef pthread_cond_t tr_cond_t; 44 #endif 45 typedef struct tr_thread_s 46 { 47 void (* func ) ( void * ); 48 void * arg; 49 char * name; 50 tr_thread_id_t thread; 51 } 52 tr_thread_t; 27 typedef struct tr_lock_s tr_lock_t; 28 typedef struct tr_cond_s tr_cond_t; 29 typedef struct tr_thread_s tr_thread_t; 53 30 54 31 const char * tr_getHomeDirectory( void ); … … 56 33 const char * tr_getTorrentsDirectory( void ); 57 34 58 /** 59 * When instantiating a thread with a deferred call to tr_threadCreate(), 60 * initializing it to THREAD_EMPTY makes calls tr_threadJoin() safe. 61 */ 62 const tr_thread_t THREAD_EMPTY; 35 tr_thread_t* tr_threadNew ( void (*func)(void *), void * arg, const char * name ); 36 void tr_threadJoin ( tr_thread_t * ); 63 37 64 void tr_threadCreate ( tr_thread_t *, void (*func)(void *), 65 void * arg, const char * name ); 66 void tr_threadJoin ( tr_thread_t * ); 67 void tr_lockInit ( tr_lock_t * ); 68 void tr_lockClose ( tr_lock_t * ); 69 int tr_lockTryLock ( tr_lock_t * ); 70 void tr_lockLock ( tr_lock_t * ); 71 void tr_lockUnlock ( tr_lock_t * ); 38 tr_lock_t * tr_lockNew ( void ); 39 void tr_lockFree ( tr_lock_t * ); 40 int tr_lockTryLock ( tr_lock_t * ); 41 void tr_lockLock ( tr_lock_t * ); 42 void tr_lockUnlock ( tr_lock_t * ); 72 43 73 void tr_condInit ( tr_cond_t *);74 void tr_condSignal( tr_cond_t * );75 void tr_condBroadcast( tr_cond_t * );76 void tr_condClose( tr_cond_t * );77 void tr_condWait ( tr_cond_t *, tr_lock_t * );44 tr_cond_t * tr_condNew ( void ); 45 void tr_condFree ( tr_cond_t * ); 46 void tr_condSignal ( tr_cond_t * ); 47 void tr_condBroadcast ( tr_cond_t * ); 48 void tr_condWait ( tr_cond_t *, tr_lock_t * ); 78 49 79 50 /*** … … 82 53 ***/ 83 54 84 typedef struct tr_rwlock_s 85 { 86 tr_lock_t lock; 87 tr_cond_t readCond; 88 tr_cond_t writeCond; 89 size_t readCount; 90 size_t wantToRead; 91 size_t wantToWrite; 92 int haveWriter; 93 } 94 tr_rwlock_t; 55 typedef struct tr_rwlock_s tr_rwlock_t; 95 56 96 void tr_rwInit ( tr_rwlock_t *);97 void tr_rwClose( tr_rwlock_t * );98 void tr_rwReaderLock ( tr_rwlock_t * );99 int tr_rwReaderTrylock ( tr_rwlock_t * );100 void tr_rwReaderUnlock ( tr_rwlock_t * );101 void tr_rwWriterLock ( tr_rwlock_t * );102 int tr_rwWriterTrylock ( tr_rwlock_t * );103 void tr_rwWriterUnlock ( tr_rwlock_t * );57 tr_rwlock_t* tr_rwNew ( void ); 58 void tr_rwFree ( tr_rwlock_t * ); 59 void tr_rwReaderLock ( tr_rwlock_t * ); 60 int tr_rwReaderTrylock ( tr_rwlock_t * ); 61 void tr_rwReaderUnlock ( tr_rwlock_t * ); 62 void tr_rwWriterLock ( tr_rwlock_t * ); 63 int tr_rwWriterTrylock ( tr_rwlock_t * ); 64 void tr_rwWriterUnlock ( tr_rwlock_t * ); 104 65 105 66 -
trunk/libtransmission/ratecontrol.c
r2544 r2552 42 42 struct tr_ratecontrol_s 43 43 { 44 tr_rwlock_t lock;44 tr_rwlock_t * lock; 45 45 int limit; 46 46 int newest; … … 78 78 tr_ratecontrol_t * r = tr_new0( tr_ratecontrol_t, 1 ); 79 79 r->limit = 0; 80 tr_rwInit( &r->lock);80 r->lock = tr_rwNew( ); 81 81 return r; 82 82 } … … 86 86 { 87 87 tr_rcReset( r ); 88 tr_rw Close( &r->lock );88 tr_rwFree( r->lock ); 89 89 tr_free( r ); 90 90 } … … 98 98 { 99 99 int ret; 100 tr_rwReaderLock( (tr_rwlock_t*) &r->lock );100 tr_rwReaderLock( (tr_rwlock_t*)r->lock ); 101 101 102 102 ret = rateForInterval( r, SHORT_INTERVAL_MSEC ) < r->limit; 103 103 104 tr_rwReaderUnlock( (tr_rwlock_t*) &r->lock );104 tr_rwReaderUnlock( (tr_rwlock_t*)r->lock ); 105 105 return ret; 106 106 } … … 110 110 { 111 111 float ret; 112 tr_rwReaderLock( (tr_rwlock_t*) &r->lock );112 tr_rwReaderLock( (tr_rwlock_t*)r->lock ); 113 113 114 114 ret = rateForInterval( r, LONG_INTERVAL_MSEC ); 115 115 116 tr_rwReaderUnlock( (tr_rwlock_t*) &r->lock );116 tr_rwReaderUnlock( (tr_rwlock_t*)r->lock ); 117 117 return ret; 118 118 } … … 130 130 return; 131 131 132 tr_rwWriterLock( &r->lock );132 tr_rwWriterLock( r->lock ); 133 133 134 134 now = tr_date (); … … 141 141 } 142 142 143 tr_rwWriterUnlock( &r->lock );143 tr_rwWriterUnlock( r->lock ); 144 144 } 145 145 … … 147 147 tr_rcReset( tr_ratecontrol_t * r ) 148 148 { 149 tr_rwWriterLock( &r->lock );149 tr_rwWriterLock( r->lock ); 150 150 r->newest = 0; 151 151 memset( r->transfers, 0, sizeof(tr_transfer_t) * HISTORY_SIZE ); 152 tr_rwWriterUnlock( &r->lock );152 tr_rwWriterUnlock( r->lock ); 153 153 } 154 154 … … 156 156 tr_rcSetLimit( tr_ratecontrol_t * r, int limit ) 157 157 { 158 tr_rwWriterLock( &r->lock );158 tr_rwWriterLock( r->lock ); 159 159 r->limit = limit; 160 tr_rwWriterUnlock( &r->lock );160 tr_rwWriterUnlock( r->lock ); 161 161 } 162 162 -
trunk/libtransmission/shared.c
r2544 r2552 47 47 { 48 48 tr_handle_t * h; 49 volatile int die;50 tr_thread_t thread;51 tr_lock_t lock;49 volatile int die; 50 tr_thread_t * thread; 51 tr_lock_t * lock; 52 52 53 53 /* Incoming connections */ … … 85 85 tr_shared_t * s = calloc( 1, sizeof( tr_shared_t ) ); 86 86 87 s->h = h; 88 tr_lockInit( &s->lock ); 89 87 s->h = h; 88 s->lock = tr_lockNew( ); 90 89 s->publicPort = -1; 91 90 s->bindPort = -1; … … 94 93 s->upnp = tr_upnpInit(); 95 94 s->choking = tr_chokingInit( h ); 96 97 /* Launch the thread */ 98 s->die = 0; 99 tr_threadCreate( &s->thread, SharedLoop, s, "shared" ); 95 s->die = 0; 96 s->thread = tr_threadNew( SharedLoop, s, "shared" ); 100 97 101 98 return s; … … 113 110 /* Stop the thread */ 114 111 s->die = 1; 115 tr_threadJoin( &s->thread );112 tr_threadJoin( s->thread ); 116 113 117 114 /* Clean up */ … … 124 121 tr_netClose( s->bindSocket ); 125 122 } 126 tr_lock Close( &s->lock );123 tr_lockFree( s->lock ); 127 124 tr_natpmpClose( s->natpmp ); 128 125 tr_upnpClose( s->upnp ); … … 138 135 void tr_sharedLock( tr_shared_t * s ) 139 136 { 140 tr_lockLock( &s->lock );137 tr_lockLock( s->lock ); 141 138 } 142 139 void tr_sharedUnlock( tr_shared_t * s ) 143 140 { 144 tr_lockUnlock( &s->lock );141 tr_lockUnlock( s->lock ); 145 142 } 146 143 -
trunk/libtransmission/torrent.c
r2544 r2552 47 47 tr_torrentReaderLock( const tr_torrent_t * tor ) 48 48 { 49 tr_rwReaderLock ( (tr_rwlock_t*) &tor->lock );49 tr_rwReaderLock ( (tr_rwlock_t*)tor->lock ); 50 50 } 51 51 … … 53 53 tr_torrentReaderUnlock( const tr_torrent_t * tor ) 54 54 { 55 tr_rwReaderUnlock ( (tr_rwlock_t*) &tor->lock );55 tr_rwReaderUnlock ( (tr_rwlock_t*)tor->lock ); 56 56 } 57 57 … … 59 59 tr_torrentWriterLock( tr_torrent_t * tor ) 60 60 { 61 tr_rwWriterLock ( &tor->lock );61 tr_rwWriterLock ( tor->lock ); 62 62 } 63 63 … … 65 65 tr_torrentWriterUnlock( tr_torrent_t * tor ) 66 66 { 67 tr_rwWriterUnlock ( &tor->lock );67 tr_rwWriterUnlock ( tor->lock ); 68 68 } 69 69 … … 260 260 tr_torrentInitFilePieces( tor ); 261 261 262 tor->thread = THREAD_EMPTY; 263 tr_rwInit( &tor->lock ); 262 tor->lock = tr_rwNew( ); 264 263 265 264 tor->upload = tr_rcInit(); … … 306 305 307 306 snprintf( name, sizeof( name ), "torrent %p (%s)", tor, tor->info.name ); 308 t r_threadCreate( &tor->thread,torrentThreadLoop, tor, name );307 tor->thread = tr_threadNew( torrentThreadLoop, tor, name ); 309 308 } 310 309 … … 1043 1042 tr_sharedLock( h->shared ); 1044 1043 1045 tr_rw Close( &tor->lock );1044 tr_rwFree( tor->lock ); 1046 1045 tr_cpClose( tor->completion ); 1047 1046 … … 1098 1097 torrentThreadLoop ( void * _tor ) 1099 1098 { 1100 static tr_lock_t checkFilesLock; 1101 static int checkFilesLockInited = FALSE; 1099 static tr_lock_t * checkFilesLock = NULL; 1102 1100 tr_torrent_t * tor = _tor; 1103 1101 1104 1102 /* create the check-files mutex */ 1105 if( !checkFilesLockInited ) { 1106 checkFilesLockInited = TRUE; 1107 tr_lockInit( &checkFilesLock ); 1108 } 1103 if( !checkFilesLock ) 1104 checkFilesLock = tr_lockNew( ); 1109 1105 1110 1106 /* loop until the torrent is being deleted */ … … 1174 1170 if( tor->uncheckedPieces ) 1175 1171 { 1176 if( !tr_lockTryLock( &checkFilesLock ) )1172 if( !tr_lockTryLock( checkFilesLock ) ) 1177 1173 { 1178 1174 run_status_t realStatus; … … 1190 1186 tr_torrentWriterUnlock( tor ); 1191 1187 1192 tr_lockUnlock( &checkFilesLock );1188 tr_lockUnlock( checkFilesLock ); 1193 1189 } 1194 1190 continue; -
trunk/libtransmission/utils.c
r2544 r2552 51 51 void tr_msgInit( void ) 52 52 { 53 if( NULL == messageLock ) 54 { 55 messageLock = calloc( 1, sizeof( *messageLock ) ); 56 tr_lockInit( messageLock ); 57 } 53 if( !messageLock ) 54 messageLock = tr_lockNew( ); 58 55 } 59 56
Note: See TracChangeset
for help on using the changeset viewer.