Mercurial > hg > nginx
comparison src/core/ngx_resolver.c @ 6357:838946300825 stable-1.8
Resolver: fixed CNAME processing for several requests.
When several requests were waiting for a response, then after getting
a CNAME response only the last request was properly processed, while
others were left waiting.
author | Ruslan Ermilov <ru@nginx.com> |
---|---|
date | Tue, 26 Jan 2016 16:46:38 +0300 |
parents | f63dd04c1580 |
children | 5557bf31e25d |
comparison
equal
deleted
inserted
replaced
6356:f63dd04c1580 | 6357:838946300825 |
---|---|
471 { | 471 { |
472 uint32_t hash; | 472 uint32_t hash; |
473 ngx_int_t rc; | 473 ngx_int_t rc; |
474 ngx_uint_t naddrs; | 474 ngx_uint_t naddrs; |
475 ngx_addr_t *addrs; | 475 ngx_addr_t *addrs; |
476 ngx_resolver_ctx_t *next; | 476 ngx_resolver_ctx_t *next, *last; |
477 ngx_resolver_node_t *rn; | 477 ngx_resolver_node_t *rn; |
478 | 478 |
479 ngx_strlow(ctx->name.data, ctx->name.data, ctx->name.len); | 479 ngx_strlow(ctx->name.data, ctx->name.data, ctx->name.len); |
480 | 480 |
481 hash = ngx_crc32_short(ctx->name.data, ctx->name.len); | 481 hash = ngx_crc32_short(ctx->name.data, ctx->name.len); |
482 | 482 |
483 rn = ngx_resolver_lookup_name(r, &ctx->name, hash); | 483 rn = ngx_resolver_lookup_name(r, &ctx->name, hash); |
484 | 484 |
485 if (rn) { | 485 if (rn) { |
486 | |
487 /* ctx can be a list after NGX_RESOLVE_CNAME */ | |
488 for (last = ctx; last->next; last = last->next); | |
486 | 489 |
487 if (rn->valid >= ngx_time()) { | 490 if (rn->valid >= ngx_time()) { |
488 | 491 |
489 ngx_log_debug0(NGX_LOG_DEBUG_CORE, r->log, 0, "resolve cached"); | 492 ngx_log_debug0(NGX_LOG_DEBUG_CORE, r->log, 0, "resolve cached"); |
490 | 493 |
509 if (addrs == NULL) { | 512 if (addrs == NULL) { |
510 return NGX_ERROR; | 513 return NGX_ERROR; |
511 } | 514 } |
512 } | 515 } |
513 | 516 |
514 ctx->next = rn->waiting; | 517 last->next = rn->waiting; |
515 rn->waiting = NULL; | 518 rn->waiting = NULL; |
516 | 519 |
517 /* unlock name mutex */ | 520 /* unlock name mutex */ |
518 | 521 |
519 do { | 522 do { |
555 ctx->name.data = rn->u.cname; | 558 ctx->name.data = rn->u.cname; |
556 | 559 |
557 return ngx_resolve_name_locked(r, ctx); | 560 return ngx_resolve_name_locked(r, ctx); |
558 } | 561 } |
559 | 562 |
560 ctx->next = rn->waiting; | 563 last->next = rn->waiting; |
561 rn->waiting = NULL; | 564 rn->waiting = NULL; |
562 | 565 |
563 /* unlock name mutex */ | 566 /* unlock name mutex */ |
564 | 567 |
565 do { | 568 do { |
588 ctx->ident = -1; | 591 ctx->ident = -1; |
589 | 592 |
590 ngx_add_timer(ctx->event, ctx->timeout); | 593 ngx_add_timer(ctx->event, ctx->timeout); |
591 } | 594 } |
592 | 595 |
593 ctx->next = rn->waiting; | 596 last->next = rn->waiting; |
594 rn->waiting = ctx; | 597 rn->waiting = ctx; |
595 ctx->state = NGX_AGAIN; | 598 ctx->state = NGX_AGAIN; |
596 | 599 |
597 return NGX_AGAIN; | 600 return NGX_AGAIN; |
598 } | 601 } |
659 | 662 |
660 ngx_resolver_free(r, rn->query); | 663 ngx_resolver_free(r, rn->query); |
661 ngx_resolver_free(r, rn->name); | 664 ngx_resolver_free(r, rn->name); |
662 ngx_resolver_free(r, rn); | 665 ngx_resolver_free(r, rn); |
663 | 666 |
664 ctx->state = NGX_RESOLVE_NXDOMAIN; | 667 do { |
665 ctx->handler(ctx); | 668 ctx->state = NGX_RESOLVE_NXDOMAIN; |
669 next = ctx->next; | |
670 | |
671 ctx->handler(ctx); | |
672 | |
673 ctx = next; | |
674 } while (ctx); | |
666 | 675 |
667 return NGX_OK; | 676 return NGX_OK; |
668 } | 677 } |
669 | 678 |
670 rn->naddrs = (u_short) -1; | 679 rn->naddrs = (u_short) -1; |