Mercurial > hg > nginx
comparison src/stream/ngx_stream_geo_module.c @ 7213:c69c13f10502
Geo: fixed memory allocation error handling (closes #1482).
If during configuration parsing of the geo directive the memory
allocation has failed, pool used to parse configuration inside
the block, and sometimes the temporary pool were not destroyed.
author | Ruslan Ermilov <ru@nginx.com> |
---|---|
date | Wed, 21 Feb 2018 15:50:42 +0300 |
parents | 47b7ffc3339d |
children | 88aad69eccef |
comparison
equal
deleted
inserted
replaced
7212:0237af43d409 | 7213:c69c13f10502 |
---|---|
407 | 407 |
408 ngx_memzero(&ctx, sizeof(ngx_stream_geo_conf_ctx_t)); | 408 ngx_memzero(&ctx, sizeof(ngx_stream_geo_conf_ctx_t)); |
409 | 409 |
410 ctx.temp_pool = ngx_create_pool(NGX_DEFAULT_POOL_SIZE, cf->log); | 410 ctx.temp_pool = ngx_create_pool(NGX_DEFAULT_POOL_SIZE, cf->log); |
411 if (ctx.temp_pool == NULL) { | 411 if (ctx.temp_pool == NULL) { |
412 ngx_destroy_pool(pool); | |
412 return NGX_CONF_ERROR; | 413 return NGX_CONF_ERROR; |
413 } | 414 } |
414 | 415 |
415 ngx_rbtree_init(&ctx.rbtree, &ctx.sentinel, ngx_str_rbtree_insert_value); | 416 ngx_rbtree_init(&ctx.rbtree, &ctx.sentinel, ngx_str_rbtree_insert_value); |
416 | 417 |
447 | 448 |
448 len = a->nelts * sizeof(ngx_stream_geo_range_t); | 449 len = a->nelts * sizeof(ngx_stream_geo_range_t); |
449 | 450 |
450 ctx.high.low[i] = ngx_palloc(cf->pool, len + sizeof(void *)); | 451 ctx.high.low[i] = ngx_palloc(cf->pool, len + sizeof(void *)); |
451 if (ctx.high.low[i] == NULL) { | 452 if (ctx.high.low[i] == NULL) { |
452 return NGX_CONF_ERROR; | 453 goto failed; |
453 } | 454 } |
454 | 455 |
455 ngx_memcpy(ctx.high.low[i], a->elts, len); | 456 ngx_memcpy(ctx.high.low[i], a->elts, len); |
456 ctx.high.low[i][a->nelts].value = NULL; | 457 ctx.high.low[i][a->nelts].value = NULL; |
457 ctx.data_size += len + sizeof(void *); | 458 ctx.data_size += len + sizeof(void *); |
473 geo->u.high = ctx.high; | 474 geo->u.high = ctx.high; |
474 | 475 |
475 var->get_handler = ngx_stream_geo_range_variable; | 476 var->get_handler = ngx_stream_geo_range_variable; |
476 var->data = (uintptr_t) geo; | 477 var->data = (uintptr_t) geo; |
477 | 478 |
478 ngx_destroy_pool(ctx.temp_pool); | |
479 ngx_destroy_pool(pool); | |
480 | |
481 } else { | 479 } else { |
482 if (ctx.tree == NULL) { | 480 if (ctx.tree == NULL) { |
483 ctx.tree = ngx_radix_tree_create(cf->pool, -1); | 481 ctx.tree = ngx_radix_tree_create(cf->pool, -1); |
484 if (ctx.tree == NULL) { | 482 if (ctx.tree == NULL) { |
485 return NGX_CONF_ERROR; | 483 goto failed; |
486 } | 484 } |
487 } | 485 } |
488 | 486 |
489 geo->u.trees.tree = ctx.tree; | 487 geo->u.trees.tree = ctx.tree; |
490 | 488 |
491 #if (NGX_HAVE_INET6) | 489 #if (NGX_HAVE_INET6) |
492 if (ctx.tree6 == NULL) { | 490 if (ctx.tree6 == NULL) { |
493 ctx.tree6 = ngx_radix_tree_create(cf->pool, -1); | 491 ctx.tree6 = ngx_radix_tree_create(cf->pool, -1); |
494 if (ctx.tree6 == NULL) { | 492 if (ctx.tree6 == NULL) { |
495 return NGX_CONF_ERROR; | 493 goto failed; |
496 } | 494 } |
497 } | 495 } |
498 | 496 |
499 geo->u.trees.tree6 = ctx.tree6; | 497 geo->u.trees.tree6 = ctx.tree6; |
500 #endif | 498 #endif |
501 | 499 |
502 var->get_handler = ngx_stream_geo_cidr_variable; | 500 var->get_handler = ngx_stream_geo_cidr_variable; |
503 var->data = (uintptr_t) geo; | 501 var->data = (uintptr_t) geo; |
504 | |
505 ngx_destroy_pool(ctx.temp_pool); | |
506 ngx_destroy_pool(pool); | |
507 | 502 |
508 if (ngx_radix32tree_insert(ctx.tree, 0, 0, | 503 if (ngx_radix32tree_insert(ctx.tree, 0, 0, |
509 (uintptr_t) &ngx_stream_variable_null_value) | 504 (uintptr_t) &ngx_stream_variable_null_value) |
510 == NGX_ERROR) | 505 == NGX_ERROR) |
511 { | 506 { |
512 return NGX_CONF_ERROR; | 507 goto failed; |
513 } | 508 } |
514 | 509 |
515 /* NGX_BUSY is okay (default was set explicitly) */ | 510 /* NGX_BUSY is okay (default was set explicitly) */ |
516 | 511 |
517 #if (NGX_HAVE_INET6) | 512 #if (NGX_HAVE_INET6) |
518 if (ngx_radix128tree_insert(ctx.tree6, zero.s6_addr, zero.s6_addr, | 513 if (ngx_radix128tree_insert(ctx.tree6, zero.s6_addr, zero.s6_addr, |
519 (uintptr_t) &ngx_stream_variable_null_value) | 514 (uintptr_t) &ngx_stream_variable_null_value) |
520 == NGX_ERROR) | 515 == NGX_ERROR) |
521 { | 516 { |
522 return NGX_CONF_ERROR; | 517 goto failed; |
523 } | 518 } |
524 #endif | 519 #endif |
525 } | 520 } |
526 | 521 |
522 ngx_destroy_pool(ctx.temp_pool); | |
523 ngx_destroy_pool(pool); | |
524 | |
527 return rv; | 525 return rv; |
526 | |
527 failed: | |
528 | |
529 ngx_destroy_pool(ctx.temp_pool); | |
530 ngx_destroy_pool(pool); | |
531 | |
532 return NGX_CONF_ERROR; | |
528 } | 533 } |
529 | 534 |
530 | 535 |
531 static char * | 536 static char * |
532 ngx_stream_geo(ngx_conf_t *cf, ngx_command_t *dummy, void *conf) | 537 ngx_stream_geo(ngx_conf_t *cf, ngx_command_t *dummy, void *conf) |