diff options
-rw-r--r-- | opentracker.c | 111 |
1 files changed, 58 insertions, 53 deletions
diff --git a/opentracker.c b/opentracker.c index 34a393e..270f6c1 100644 --- a/opentracker.c +++ b/opentracker.c | |||
@@ -385,21 +385,12 @@ void help( char *name ) { | |||
385 | ); | 385 | ); |
386 | } | 386 | } |
387 | 387 | ||
388 | void handle_read( int64 clientsocket, int afteraccept ) { | 388 | void handle_read( int64 clientsocket ) { |
389 | struct http_data* h = io_getcookie( clientsocket ); | 389 | struct http_data* h = io_getcookie( clientsocket ); |
390 | int l = io_tryread( clientsocket, static_scratch, sizeof static_scratch ); | 390 | int l = io_tryread( clientsocket, static_scratch, sizeof static_scratch ); |
391 | tai6464 t; | 391 | tai6464 t; |
392 | 392 | ||
393 | taia_now(&t); | ||
394 | taia_addsec(&t,&t,OT_CLIENT_TIMEOUT); | ||
395 | io_timeout(clientsocket,t); | ||
396 | |||
397 | if( l <= 0 ) { | 393 | if( l <= 0 ) { |
398 | // getting 0 bytes doesn't mean connection closed, | ||
399 | // when we try the shortcut read() after accept() | ||
400 | // and nothing is there yet | ||
401 | if( afteraccept && ( errno == EAGAIN ) ) | ||
402 | return; | ||
403 | if( h ) { | 394 | if( h ) { |
404 | array_reset(&h->r); | 395 | array_reset(&h->r); |
405 | free(h); | 396 | free(h); |
@@ -416,69 +407,83 @@ void handle_read( int64 clientsocket, int afteraccept ) { | |||
416 | httperror(clientsocket,h,"500 request too long","You sent too much headers"); | 407 | httperror(clientsocket,h,"500 request too long","You sent too much headers"); |
417 | else if ((l=header_complete(h))) | 408 | else if ((l=header_complete(h))) |
418 | httpresponse(clientsocket,h); | 409 | httpresponse(clientsocket,h); |
410 | else { | ||
411 | taia_now(&t); | ||
412 | taia_addsec(&t,&t,OT_CLIENT_TIMEOUT); | ||
413 | io_timeout(clientsocket,t); | ||
414 | } | ||
419 | } | 415 | } |
420 | 416 | ||
421 | void server_mainloop( int64 serversocket ) { | 417 | void handle_accept( int64 serversocket ) { |
422 | tai6464 t, next_timeout_check; | 418 | struct http_data* h; |
423 | unsigned char ip[4]; | 419 | unsigned char ip[4]; |
424 | uint16 port; | 420 | uint16 port; |
421 | tai6464 t; | ||
422 | int64 i; | ||
423 | |||
424 | while( ( i = socket_accept4( serversocket, (char*)ip, &port) ) != -1 ) { | ||
425 | |||
426 | if( !io_fd( i ) || | ||
427 | !(h = (struct http_data*)malloc(sizeof(struct http_data))) ) { | ||
428 | io_close( i ); | ||
429 | continue; | ||
430 | } | ||
431 | |||
432 | io_wantread( i ); | ||
433 | |||
434 | byte_zero(h,sizeof(struct http_data)); | ||
435 | memmove(h->ip,ip,sizeof(ip)); | ||
436 | io_setcookie(i,h); | ||
437 | ++ot_overall_connections; | ||
438 | taia_now(&t); | ||
439 | taia_addsec(&t,&t,OT_CLIENT_TIMEOUT); | ||
440 | io_timeout(i,t); | ||
441 | } | ||
442 | |||
443 | if( errno==EAGAIN ) | ||
444 | io_eagain( serversocket ); | ||
445 | else | ||
446 | carp( "socket_accept4" ); | ||
447 | } | ||
448 | |||
449 | void handle_timeouted( ) { | ||
450 | int64 i; | ||
451 | while( ( i = io_timeouted() ) != -1 ) { | ||
452 | struct http_data* h=io_getcookie(i); | ||
453 | if( h ) { | ||
454 | array_reset( &h->r ); | ||
455 | free( h ); | ||
456 | } | ||
457 | io_close(i); | ||
458 | } | ||
459 | } | ||
460 | |||
461 | void server_mainloop( int64 serversocket ) { | ||
462 | tai6464 t, next_timeout_check; | ||
425 | 463 | ||
426 | io_wantread( serversocket ); | 464 | io_wantread( serversocket ); |
427 | taia_now( &next_timeout_check ); | 465 | taia_now( &next_timeout_check ); |
428 | 466 | ||
429 | for (;;) { | 467 | for (;;) { |
430 | int64 i; | 468 | int64 i; |
431 | int handled_connections = 1024; | ||
432 | 469 | ||
433 | taia_now(&t); | 470 | taia_now(&t); |
434 | taia_addsec(&t,&t,OT_CLIENT_TIMEOUT_CHECKINTERVAL); | 471 | taia_addsec(&t,&t,OT_CLIENT_TIMEOUT_CHECKINTERVAL); |
435 | io_waituntil(t); | 472 | io_waituntil(t); |
436 | 473 | ||
474 | while( ( i = io_canread() ) != -1 ) { | ||
475 | if( i == serversocket ) | ||
476 | handle_accept( i ); | ||
477 | else | ||
478 | handle_read( i ); | ||
479 | } | ||
480 | |||
437 | taia_now(&t); | 481 | taia_now(&t); |
438 | if( taia_less( &next_timeout_check, &t ) ) { | 482 | if( taia_less( &next_timeout_check, &t ) ) { |
439 | while( ( i = io_timeouted() ) != -1 ) { | 483 | handle_timeouted( ); |
440 | struct http_data* h=io_getcookie(i); | ||
441 | if( h ) { | ||
442 | array_reset( &h->r ); | ||
443 | free( h ); | ||
444 | } | ||
445 | io_close(i); | ||
446 | } | ||
447 | taia_now(&next_timeout_check); | 484 | taia_now(&next_timeout_check); |
448 | taia_addsec(&next_timeout_check,&next_timeout_check,OT_CLIENT_TIMEOUT_CHECKINTERVAL); | 485 | taia_addsec(&next_timeout_check,&next_timeout_check,OT_CLIENT_TIMEOUT_CHECKINTERVAL); |
449 | } | 486 | } |
450 | |||
451 | while( --handled_connections && ( ( i = io_canread() ) != -1 ) ) { | ||
452 | |||
453 | if( i != serversocket ) { | ||
454 | handle_read( i, 0 ); | ||
455 | continue; | ||
456 | } | ||
457 | |||
458 | // Attention, i changes from what io_canread() returned to | ||
459 | // what socket_accept4 returns as new socket | ||
460 | while( ( i = socket_accept4( serversocket, (char*)ip, &port) ) != -1 ) { | ||
461 | if( io_fd( i ) ) { | ||
462 | struct http_data* h=(struct http_data*)malloc(sizeof(struct http_data)); | ||
463 | io_wantread( i ); | ||
464 | |||
465 | if (h) { | ||
466 | byte_zero(h,sizeof(struct http_data)); | ||
467 | memmove(h->ip,ip,sizeof(ip)); | ||
468 | io_setcookie(i,h); | ||
469 | ++ot_overall_connections; | ||
470 | handle_read(i,1); | ||
471 | } else | ||
472 | io_close(i); | ||
473 | } else | ||
474 | io_close(i); | ||
475 | } | ||
476 | |||
477 | if( errno==EAGAIN ) | ||
478 | io_eagain( serversocket ); | ||
479 | else | ||
480 | carp( "socket_accept4" ); | ||
481 | } | ||
482 | } | 487 | } |
483 | } | 488 | } |
484 | 489 | ||