comparison src/http/ngx_http_core_module.c @ 550:1dcf6adad484 NGINX_0_8_21

nginx 0.8.21 *) Feature: now the "-V" switch shows TLS SNI support. *) Feature: the "listen" directive of the HTTP module supports unix domain sockets. Thanks to Hongli Lai. *) Feature: the "default_server" parameter of the "listen" directive. *) Feature: now a "default" parameter is not required to set listen socket options. *) Bugfix: nginx did not support dates in 2038 year on 32-bit platforms; *) Bugfix: socket leak; the bug had appeared in 0.8.11.
author Igor Sysoev <http://sysoev.ru>
date Mon, 26 Oct 2009 00:00:00 +0300
parents f7ec98e3caeb
children c04fa65fe604
comparison
equal deleted inserted replaced
549:3ca2e495d9de 550:1dcf6adad484
2805 * set by ngx_pcalloc(): 2805 * set by ngx_pcalloc():
2806 * 2806 *
2807 * conf->client_large_buffers.num = 0; 2807 * conf->client_large_buffers.num = 0;
2808 */ 2808 */
2809 2809
2810 if (ngx_array_init(&cscf->listen, cf->temp_pool, 4,
2811 sizeof(ngx_http_listen_t))
2812 != NGX_OK)
2813 {
2814 return NULL;
2815 }
2816
2817 if (ngx_array_init(&cscf->server_names, cf->temp_pool, 4, 2810 if (ngx_array_init(&cscf->server_names, cf->temp_pool, 4,
2818 sizeof(ngx_http_server_name_t)) 2811 sizeof(ngx_http_server_name_t))
2819 != NGX_OK) 2812 != NGX_OK)
2820 { 2813 {
2821 return NULL; 2814 return NULL;
2837 ngx_http_core_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child) 2830 ngx_http_core_merge_srv_conf(ngx_conf_t *cf, void *parent, void *child)
2838 { 2831 {
2839 ngx_http_core_srv_conf_t *prev = parent; 2832 ngx_http_core_srv_conf_t *prev = parent;
2840 ngx_http_core_srv_conf_t *conf = child; 2833 ngx_http_core_srv_conf_t *conf = child;
2841 2834
2842 ngx_http_listen_t *ls;
2843 struct sockaddr_in *sin; 2835 struct sockaddr_in *sin;
2836 ngx_http_listen_opt_t lsopt;
2844 ngx_http_server_name_t *sn; 2837 ngx_http_server_name_t *sn;
2845 2838
2846 /* TODO: it does not merge, it inits only */ 2839 /* TODO: it does not merge, it inits only */
2847 2840
2848 if (conf->listen.nelts == 0) { 2841 if (!conf->listen) {
2849 ls = ngx_array_push(&conf->listen); 2842 ngx_memzero(&lsopt, sizeof(ngx_http_listen_opt_t));
2850 if (ls == NULL) { 2843
2851 return NGX_CONF_ERROR; 2844 sin = (struct sockaddr_in *) &lsopt.sockaddr;
2852 }
2853
2854 ngx_memzero(ls, sizeof(ngx_http_listen_t));
2855
2856 sin = (struct sockaddr_in *) &ls->sockaddr;
2857 2845
2858 sin->sin_family = AF_INET; 2846 sin->sin_family = AF_INET;
2859 #if (NGX_WIN32) 2847 #if (NGX_WIN32)
2860 sin->sin_port = htons(80); 2848 sin->sin_port = htons(80);
2861 #else 2849 #else
2862 sin->sin_port = htons((getuid() == 0) ? 80 : 8000); 2850 sin->sin_port = htons((getuid() == 0) ? 80 : 8000);
2863 #endif 2851 #endif
2864 sin->sin_addr.s_addr = INADDR_ANY; 2852 sin->sin_addr.s_addr = INADDR_ANY;
2865 2853
2866 ls->socklen = sizeof(struct sockaddr_in); 2854 lsopt.socklen = sizeof(struct sockaddr_in);
2867 2855
2868 ls->conf.backlog = NGX_LISTEN_BACKLOG; 2856 lsopt.backlog = NGX_LISTEN_BACKLOG;
2869 ls->conf.rcvbuf = -1; 2857 lsopt.rcvbuf = -1;
2870 ls->conf.sndbuf = -1; 2858 lsopt.sndbuf = -1;
2871 ls->conf.wildcard = 1; 2859 lsopt.wildcard = 1;
2872 2860
2873 (void) ngx_sock_ntop((struct sockaddr *) &ls->sockaddr, ls->conf.addr, 2861 (void) ngx_sock_ntop((struct sockaddr *) &lsopt.sockaddr, lsopt.addr,
2874 NGX_SOCKADDR_STRLEN, 1); 2862 NGX_SOCKADDR_STRLEN, 1);
2863
2864 if (ngx_http_add_listen(cf, conf, &lsopt) == NGX_OK) {
2865 return NGX_CONF_OK;
2866 }
2875 } 2867 }
2876 2868
2877 if (conf->server_name.data == NULL) { 2869 if (conf->server_name.data == NULL) {
2878 conf->server_name = cf->cycle->hostname; 2870 conf->server_name = cf->cycle->hostname;
2879 2871
2882 return NGX_CONF_ERROR; 2874 return NGX_CONF_ERROR;
2883 } 2875 }
2884 2876
2885 #if (NGX_PCRE) 2877 #if (NGX_PCRE)
2886 sn->regex = NULL; 2878 sn->regex = NULL;
2887 sn->captures = 0;
2888 #endif 2879 #endif
2889 sn->core_srv_conf = conf; 2880 sn->server = conf;
2890 sn->name.len = conf->server_name.len; 2881 sn->name.len = conf->server_name.len;
2891 sn->name.data = conf->server_name.data; 2882 sn->name.data = conf->server_name.data;
2892 } 2883 }
2893 2884
2894 ngx_conf_merge_size_value(conf->connection_pool_size, 2885 ngx_conf_merge_size_value(conf->connection_pool_size,
3271 3262
3272 3263
3273 static char * 3264 static char *
3274 ngx_http_core_listen(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) 3265 ngx_http_core_listen(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
3275 { 3266 {
3276 ngx_http_core_srv_conf_t *scf = conf; 3267 ngx_http_core_srv_conf_t *cscf = conf;
3277 3268
3278 ngx_str_t *value, size; 3269 ngx_str_t *value, size;
3279 ngx_url_t u; 3270 ngx_url_t u;
3280 ngx_uint_t n; 3271 ngx_uint_t n;
3281 ngx_http_listen_t *ls; 3272 ngx_http_listen_opt_t lsopt;
3282 3273
3283 /* 3274 cscf->listen = 1;
3284 * TODO: check duplicate 'listen' directives,
3285 * add resolved name to server names ???
3286 */
3287 3275
3288 value = cf->args->elts; 3276 value = cf->args->elts;
3289 3277
3290 ngx_memzero(&u, sizeof(ngx_url_t)); 3278 ngx_memzero(&u, sizeof(ngx_url_t));
3291 3279
3301 } 3289 }
3302 3290
3303 return NGX_CONF_ERROR; 3291 return NGX_CONF_ERROR;
3304 } 3292 }
3305 3293
3306 ls = ngx_array_push(&scf->listen); 3294 ngx_memzero(&lsopt, sizeof(ngx_http_listen_opt_t));
3307 if (ls == NULL) { 3295
3308 return NGX_CONF_ERROR; 3296 ngx_memcpy(lsopt.sockaddr, u.sockaddr, u.socklen);
3309 } 3297
3310 3298 lsopt.socklen = u.socklen;
3311 ngx_memzero(ls, sizeof(ngx_http_listen_t)); 3299 lsopt.backlog = NGX_LISTEN_BACKLOG;
3312 3300 lsopt.rcvbuf = -1;
3313 ngx_memcpy(ls->sockaddr, u.sockaddr, u.socklen); 3301 lsopt.sndbuf = -1;
3314 3302 lsopt.wildcard = u.wildcard;
3315 ls->socklen = u.socklen; 3303
3316 ls->file_name = cf->conf_file->file.name.data; 3304 (void) ngx_sock_ntop((struct sockaddr *) &lsopt.sockaddr, lsopt.addr,
3317 ls->line = cf->conf_file->line;
3318 ls->conf.backlog = NGX_LISTEN_BACKLOG;
3319 ls->conf.rcvbuf = -1;
3320 ls->conf.sndbuf = -1;
3321 ls->conf.wildcard = u.wildcard;
3322
3323 (void) ngx_sock_ntop((struct sockaddr *) &ls->sockaddr, ls->conf.addr,
3324 NGX_SOCKADDR_STRLEN, 1); 3305 NGX_SOCKADDR_STRLEN, 1);
3325 3306
3326 if (cf->args->nelts == 2) { 3307 for (n = 2; n < cf->args->nelts; n++) {
3327 return NGX_CONF_OK; 3308
3328 } 3309 if (ngx_strcmp(value[n].data, "default_server") == 0
3329 3310 || ngx_strcmp(value[n].data, "default") == 0)
3330 if (ngx_strcmp(value[2].data, "default") == 0) { 3311 {
3331 ls->conf.default_server = 1; 3312 lsopt.default_server = 1;
3332 n = 3; 3313 continue;
3333
3334 } else {
3335 n = 2;
3336 }
3337
3338 for ( /* void */ ; n < cf->args->nelts; n++) {
3339
3340 if (ls->conf.default_server == 0) {
3341 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3342 "\"%V\" parameter can be specified for "
3343 "the default \"listen\" directive only",
3344 &value[n]);
3345 return NGX_CONF_ERROR;
3346 } 3314 }
3347 3315
3348 if (ngx_strcmp(value[n].data, "bind") == 0) { 3316 if (ngx_strcmp(value[n].data, "bind") == 0) {
3349 ls->conf.bind = 1; 3317 lsopt.set = 1;
3318 lsopt.bind = 1;
3350 continue; 3319 continue;
3351 } 3320 }
3352 3321
3353 if (ngx_strncmp(value[n].data, "backlog=", 8) == 0) { 3322 if (ngx_strncmp(value[n].data, "backlog=", 8) == 0) {
3354 ls->conf.backlog = ngx_atoi(value[n].data + 8, value[n].len - 8); 3323 lsopt.backlog = ngx_atoi(value[n].data + 8, value[n].len - 8);
3355 ls->conf.bind = 1; 3324 lsopt.set = 1;
3356 3325 lsopt.bind = 1;
3357 if (ls->conf.backlog == NGX_ERROR || ls->conf.backlog == 0) { 3326
3327 if (lsopt.backlog == NGX_ERROR || lsopt.backlog == 0) {
3358 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3328 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3359 "invalid backlog \"%V\"", &value[n]); 3329 "invalid backlog \"%V\"", &value[n]);
3360 return NGX_CONF_ERROR; 3330 return NGX_CONF_ERROR;
3361 } 3331 }
3362 3332
3365 3335
3366 if (ngx_strncmp(value[n].data, "rcvbuf=", 7) == 0) { 3336 if (ngx_strncmp(value[n].data, "rcvbuf=", 7) == 0) {
3367 size.len = value[n].len - 7; 3337 size.len = value[n].len - 7;
3368 size.data = value[n].data + 7; 3338 size.data = value[n].data + 7;
3369 3339
3370 ls->conf.rcvbuf = ngx_parse_size(&size); 3340 lsopt.rcvbuf = ngx_parse_size(&size);
3371 ls->conf.bind = 1; 3341 lsopt.set = 1;
3372 3342 lsopt.bind = 1;
3373 if (ls->conf.rcvbuf == NGX_ERROR) { 3343
3344 if (lsopt.rcvbuf == NGX_ERROR) {
3374 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3345 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3375 "invalid rcvbuf \"%V\"", &value[n]); 3346 "invalid rcvbuf \"%V\"", &value[n]);
3376 return NGX_CONF_ERROR; 3347 return NGX_CONF_ERROR;
3377 } 3348 }
3378 3349
3381 3352
3382 if (ngx_strncmp(value[n].data, "sndbuf=", 7) == 0) { 3353 if (ngx_strncmp(value[n].data, "sndbuf=", 7) == 0) {
3383 size.len = value[n].len - 7; 3354 size.len = value[n].len - 7;
3384 size.data = value[n].data + 7; 3355 size.data = value[n].data + 7;
3385 3356
3386 ls->conf.sndbuf = ngx_parse_size(&size); 3357 lsopt.sndbuf = ngx_parse_size(&size);
3387 ls->conf.bind = 1; 3358 lsopt.set = 1;
3388 3359 lsopt.bind = 1;
3389 if (ls->conf.sndbuf == NGX_ERROR) { 3360
3361 if (lsopt.sndbuf == NGX_ERROR) {
3390 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3362 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3391 "invalid sndbuf \"%V\"", &value[n]); 3363 "invalid sndbuf \"%V\"", &value[n]);
3392 return NGX_CONF_ERROR; 3364 return NGX_CONF_ERROR;
3393 } 3365 }
3394 3366
3395 continue; 3367 continue;
3396 } 3368 }
3397 3369
3398 if (ngx_strncmp(value[n].data, "accept_filter=", 14) == 0) { 3370 if (ngx_strncmp(value[n].data, "accept_filter=", 14) == 0) {
3399 #if (NGX_HAVE_DEFERRED_ACCEPT && defined SO_ACCEPTFILTER) 3371 #if (NGX_HAVE_DEFERRED_ACCEPT && defined SO_ACCEPTFILTER)
3400 ls->conf.accept_filter = (char *) &value[n].data[14]; 3372 lsopt.accept_filter = (char *) &value[n].data[14];
3401 ls->conf.bind = 1; 3373 lsopt.set = 1;
3374 lsopt.bind = 1;
3402 #else 3375 #else
3403 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3376 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3404 "accept filters \"%V\" are not supported " 3377 "accept filters \"%V\" are not supported "
3405 "on this platform, ignored", 3378 "on this platform, ignored",
3406 &value[n]); 3379 &value[n]);
3408 continue; 3381 continue;
3409 } 3382 }
3410 3383
3411 if (ngx_strcmp(value[n].data, "deferred") == 0) { 3384 if (ngx_strcmp(value[n].data, "deferred") == 0) {
3412 #if (NGX_HAVE_DEFERRED_ACCEPT && defined TCP_DEFER_ACCEPT) 3385 #if (NGX_HAVE_DEFERRED_ACCEPT && defined TCP_DEFER_ACCEPT)
3413 ls->conf.deferred_accept = 1; 3386 lsopt.deferred_accept = 1;
3414 ls->conf.bind = 1; 3387 lsopt.set = 1;
3388 lsopt.bind = 1;
3415 #else 3389 #else
3416 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3390 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3417 "the deferred accept is not supported " 3391 "the deferred accept is not supported "
3418 "on this platform, ignored"); 3392 "on this platform, ignored");
3419 #endif 3393 #endif
3422 3396
3423 if (ngx_strncmp(value[n].data, "ipv6only=o", 10) == 0) { 3397 if (ngx_strncmp(value[n].data, "ipv6only=o", 10) == 0) {
3424 #if (NGX_HAVE_INET6 && defined IPV6_V6ONLY) 3398 #if (NGX_HAVE_INET6 && defined IPV6_V6ONLY)
3425 struct sockaddr *sa; 3399 struct sockaddr *sa;
3426 3400
3427 sa = (struct sockaddr *) ls->sockaddr; 3401 sa = (struct sockaddr *) lsopt.sockaddr;
3428 3402
3429 if (sa->sa_family == AF_INET6) { 3403 if (sa->sa_family == AF_INET6) {
3430 3404
3431 if (ngx_strcmp(&value[n].data[10], "n") == 0) { 3405 if (ngx_strcmp(&value[n].data[10], "n") == 0) {
3432 ls->conf.ipv6only = 1; 3406 lsopt.ipv6only = 1;
3433 3407
3434 } else if (ngx_strcmp(&value[n].data[10], "ff") == 0) { 3408 } else if (ngx_strcmp(&value[n].data[10], "ff") == 0) {
3435 ls->conf.ipv6only = 2; 3409 lsopt.ipv6only = 2;
3436 3410
3437 } else { 3411 } else {
3438 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3412 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3439 "invalid ipv6only flags \"%s\"", 3413 "invalid ipv6only flags \"%s\"",
3440 &value[n].data[9]); 3414 &value[n].data[9]);
3441 return NGX_CONF_ERROR; 3415 return NGX_CONF_ERROR;
3442 } 3416 }
3443 3417
3444 ls->conf.bind = 1; 3418 lsopt.set = 1;
3419 lsopt.bind = 1;
3445 3420
3446 } else { 3421 } else {
3447 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3422 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3448 "ipv6only is not supported " 3423 "ipv6only is not supported "
3449 "on addr \"%s\", ignored", 3424 "on addr \"%s\", ignored", lsopt.addr);
3450 ls->conf.addr);
3451 } 3425 }
3452 3426
3453 continue; 3427 continue;
3454 #else 3428 #else
3455 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3429 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3459 #endif 3433 #endif
3460 } 3434 }
3461 3435
3462 if (ngx_strcmp(value[n].data, "ssl") == 0) { 3436 if (ngx_strcmp(value[n].data, "ssl") == 0) {
3463 #if (NGX_HTTP_SSL) 3437 #if (NGX_HTTP_SSL)
3464 ls->conf.ssl = 1; 3438 lsopt.set = 1;
3439 lsopt.ssl = 1;
3465 continue; 3440 continue;
3466 #else 3441 #else
3467 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3442 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3468 "the \"ssl\" parameter requires " 3443 "the \"ssl\" parameter requires "
3469 "ngx_http_ssl_module"); 3444 "ngx_http_ssl_module");
3474 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3449 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3475 "the invalid \"%V\" parameter", &value[n]); 3450 "the invalid \"%V\" parameter", &value[n]);
3476 return NGX_CONF_ERROR; 3451 return NGX_CONF_ERROR;
3477 } 3452 }
3478 3453
3479 return NGX_CONF_OK; 3454 if (ngx_http_add_listen(cf, cscf, &lsopt) == NGX_OK) {
3455 return NGX_CONF_OK;
3456 }
3457
3458 return NGX_CONF_ERROR;
3480 } 3459 }
3481 3460
3482 3461
3483 static char * 3462 static char *
3484 ngx_http_core_server_name(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) 3463 ngx_http_core_server_name(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
3546 return NGX_CONF_ERROR; 3525 return NGX_CONF_ERROR;
3547 } 3526 }
3548 3527
3549 #if (NGX_PCRE) 3528 #if (NGX_PCRE)
3550 sn->regex = NULL; 3529 sn->regex = NULL;
3551 sn->captures = 0;
3552 #endif 3530 #endif
3553 sn->core_srv_conf = cscf; 3531 sn->server = cscf;
3554 sn->name = value[i]; 3532 sn->name = value[i];
3533
3534 ngx_strlow(sn->name.data, sn->name.data, sn->name.len);
3555 3535
3556 if (value[i].data[0] != '~') { 3536 if (value[i].data[0] != '~') {
3557 continue; 3537 continue;
3558 } 3538 }
3559 3539
3579 if (sn->regex == NULL) { 3559 if (sn->regex == NULL) {
3580 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, "%s", err.data); 3560 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, "%s", err.data);
3581 return NGX_CONF_ERROR; 3561 return NGX_CONF_ERROR;
3582 } 3562 }
3583 3563
3584 sn->captures = (ngx_regex_capture_count(sn->regex) > 0);
3585 sn->name = value[i]; 3564 sn->name = value[i];
3565 cscf->captures = (ngx_regex_capture_count(sn->regex) > 0);
3586 } 3566 }
3587 #else 3567 #else
3588 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 3568 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
3589 "the using of the regex \"%V\" " 3569 "the using of the regex \"%V\" "
3590 "requires PCRE library", &value[i]); 3570 "requires PCRE library", &value[i]);