comparison src/core/ngx_connection.c @ 3880:e3cb8e27e413

reuse keepalive connections if there are no free worker connections patch by Maxim Dounin
author Igor Sysoev <igor@sysoev.ru>
date Mon, 04 Apr 2011 12:26:53 +0000
parents 4430d110293e
children b044d6553d52
comparison
equal deleted inserted replaced
3879:502a6b0acf3f 3880:e3cb8e27e413
8 #include <ngx_core.h> 8 #include <ngx_core.h>
9 #include <ngx_event.h> 9 #include <ngx_event.h>
10 10
11 11
12 ngx_os_io_t ngx_io; 12 ngx_os_io_t ngx_io;
13
14
15 static void ngx_drain_connections(void);
13 16
14 17
15 ngx_listening_t * 18 ngx_listening_t *
16 ngx_create_listening(ngx_conf_t *cf, void *sockaddr, socklen_t socklen) 19 ngx_create_listening(ngx_conf_t *cf, void *sockaddr, socklen_t socklen)
17 { 20 {
717 /* ngx_mutex_lock */ 720 /* ngx_mutex_lock */
718 721
719 c = ngx_cycle->free_connections; 722 c = ngx_cycle->free_connections;
720 723
721 if (c == NULL) { 724 if (c == NULL) {
725 ngx_drain_connections();
726 c = ngx_cycle->free_connections;
727 }
728
729 if (c == NULL) {
722 ngx_log_error(NGX_LOG_ALERT, log, 0, 730 ngx_log_error(NGX_LOG_ALERT, log, 0,
723 "%ui worker_connections are not enough", 731 "%ui worker_connections are not enough",
724 ngx_cycle->connection_n); 732 ngx_cycle->connection_n);
725 733
726 /* ngx_mutex_unlock */ 734 /* ngx_mutex_unlock */
859 c->read->closed = 1; 867 c->read->closed = 1;
860 c->write->closed = 1; 868 c->write->closed = 1;
861 869
862 #endif 870 #endif
863 871
872 ngx_reusable_connection(c, 0);
873
864 log_error = c->log_error; 874 log_error = c->log_error;
865 875
866 ngx_free_connection(c); 876 ngx_free_connection(c);
867 877
868 fd = c->fd; 878 fd = c->fd;
894 904
895 /* we use ngx_cycle->log because c->log was in c->pool */ 905 /* we use ngx_cycle->log because c->log was in c->pool */
896 906
897 ngx_log_error(level, ngx_cycle->log, err, 907 ngx_log_error(level, ngx_cycle->log, err,
898 ngx_close_socket_n " %d failed", fd); 908 ngx_close_socket_n " %d failed", fd);
909 }
910 }
911
912
913 void
914 ngx_reusable_connection(ngx_connection_t *c, ngx_uint_t reusable)
915 {
916 ngx_log_debug1(NGX_LOG_DEBUG_CORE, c->log, 0,
917 "reusable connection: %ui", reusable);
918
919 if (c->reusable) {
920 ngx_queue_remove(&c->queue);
921 }
922
923 c->reusable = reusable;
924
925 if (reusable) {
926 /* need cast as ngx_cycle is volatile */
927
928 ngx_queue_insert_head(
929 (ngx_queue_t *) &ngx_cycle->reusable_connections_queue, &c->queue);
930 }
931 }
932
933
934 static void
935 ngx_drain_connections(void)
936 {
937 ngx_int_t i;
938 ngx_queue_t *q;
939 ngx_connection_t *c;
940
941 for (i = 0; i < 32; i++) {
942 if (ngx_queue_empty(&ngx_cycle->reusable_connections_queue)) {
943 break;
944 }
945
946 q = ngx_queue_last(&ngx_cycle->reusable_connections_queue);
947 c = ngx_queue_data(q, ngx_connection_t, queue);
948
949 ngx_log_debug0(NGX_LOG_DEBUG_CORE, c->log, 0,
950 "reusing connection");
951
952 c->close = 1;
953 c->read->handler(c->read);
899 } 954 }
900 } 955 }
901 956
902 957
903 ngx_int_t 958 ngx_int_t