comparison src/core/ngx_resolver.c @ 4723:68ac485abbba stable-1.2

Merge of r4654, r4672, r4684, r4685, r4692: resolver changes. *) Resolver: fixed format specification. Patch by Yichun Zhang (agentzh). *) Support for IPv6 literals and an optional port in resolver. *) Fixed crash in ngx_resolver_cleanup_tree(). If sending a DNS request fails with an error (e.g., when mistakenly trying to send it to a local IP broadcast), such a request is not deleted if there are clients waiting on it. However, it was still erroneously removed from the queue. Later ngx_resolver_cleanup_tree() attempted to remove it from the queue again that resulted in a NULL pointer dereference. *) When "resolver" is configured with a domain name, only the first resolved address was used. Now all addresses will be used. *) Fixed segfault with poll and resolver used. Poll event method needs ngx_cycle->files to work, and use of ngx_exit_cycle without files set caused null pointer dereference in resolver's cleanup on udp socket close.
author Maxim Dounin <mdounin@mdounin.ru>
date Mon, 02 Jul 2012 16:23:14 +0000
parents 474bbe8ca79c
children 9be0b6b749ae
comparison
equal deleted inserted replaced
4722:bb08178f23b0 4723:68ac485abbba
94 ngx_resolver_t * 94 ngx_resolver_t *
95 ngx_resolver_create(ngx_conf_t *cf, ngx_str_t *names, ngx_uint_t n) 95 ngx_resolver_create(ngx_conf_t *cf, ngx_str_t *names, ngx_uint_t n)
96 { 96 {
97 ngx_str_t s; 97 ngx_str_t s;
98 ngx_url_t u; 98 ngx_url_t u;
99 ngx_uint_t i; 99 ngx_uint_t i, j;
100 ngx_resolver_t *r; 100 ngx_resolver_t *r;
101 ngx_pool_cleanup_t *cln; 101 ngx_pool_cleanup_t *cln;
102 ngx_udp_connection_t *uc; 102 ngx_udp_connection_t *uc;
103 103
104 cln = ngx_pool_cleanup_add(cf->pool, 0); 104 cln = ngx_pool_cleanup_add(cf->pool, 0);
169 continue; 169 continue;
170 } 170 }
171 171
172 ngx_memzero(&u, sizeof(ngx_url_t)); 172 ngx_memzero(&u, sizeof(ngx_url_t));
173 173
174 u.host = names[i]; 174 u.url = names[i];
175 u.port = 53; 175 u.default_port = 53;
176 176
177 if (ngx_inet_resolve_host(cf->pool, &u) != NGX_OK) { 177 if (ngx_parse_url(cf->pool, &u) != NGX_OK) {
178 if (u.err) { 178 if (u.err) {
179 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, 179 ngx_conf_log_error(NGX_LOG_EMERG, cf, 0,
180 "%s in resolver \"%V\"", 180 "%s in resolver \"%V\"",
181 u.err, &u.host); 181 u.err, &u.url);
182 } 182 }
183 183
184 return NULL; 184 return NULL;
185 } 185 }
186 186
187 uc = ngx_array_push(&r->udp_connections); 187 uc = ngx_array_push_n(&r->udp_connections, u.naddrs);
188 if (uc == NULL) { 188 if (uc == NULL) {
189 return NULL; 189 return NULL;
190 } 190 }
191 191
192 ngx_memzero(uc, sizeof(ngx_udp_connection_t)); 192 ngx_memzero(uc, u.naddrs * sizeof(ngx_udp_connection_t));
193 193
194 uc->sockaddr = u.addrs->sockaddr; 194 for (j = 0; j < u.naddrs; j++) {
195 uc->socklen = u.addrs->socklen; 195 uc[j].sockaddr = u.addrs[j].sockaddr;
196 uc->server = u.addrs->name; 196 uc[j].socklen = u.addrs[j].socklen;
197 uc[j].server = u.addrs[j].name;
198 }
197 } 199 }
198 200
199 return r; 201 return r;
200 } 202 }
201 203
975 977
976 ngx_queue_remove(q); 978 ngx_queue_remove(q);
977 979
978 if (rn->waiting) { 980 if (rn->waiting) {
979 981
980 if (ngx_resolver_send_query(r, rn) == NGX_OK) { 982 (void) ngx_resolver_send_query(r, rn);
981 983
982 rn->expire = now + r->resend_timeout; 984 rn->expire = now + r->resend_timeout;
983 985
984 ngx_queue_insert_head(queue, &rn->queue); 986 ngx_queue_insert_head(queue, q);
985 }
986 987
987 continue; 988 continue;
988 } 989 }
989 990
990 ngx_rbtree_delete(tree, &rn->node); 991 ngx_rbtree_delete(tree, &rn->node);
1038 flags = (query->flags_hi << 8) + query->flags_lo; 1039 flags = (query->flags_hi << 8) + query->flags_lo;
1039 nqs = (query->nqs_hi << 8) + query->nqs_lo; 1040 nqs = (query->nqs_hi << 8) + query->nqs_lo;
1040 nan = (query->nan_hi << 8) + query->nan_lo; 1041 nan = (query->nan_hi << 8) + query->nan_lo;
1041 1042
1042 ngx_log_debug6(NGX_LOG_DEBUG_CORE, r->log, 0, 1043 ngx_log_debug6(NGX_LOG_DEBUG_CORE, r->log, 0,
1043 "resolver DNS response %ui fl:%04Xui %ui/%ui/%ui/%ui", 1044 "resolver DNS response %ui fl:%04Xui %ui/%ui/%ud/%ud",
1044 ident, flags, nqs, nan, 1045 ident, flags, nqs, nan,
1045 (query->nns_hi << 8) + query->nns_lo, 1046 (query->nns_hi << 8) + query->nns_lo,
1046 (query->nar_hi << 8) + query->nar_lo); 1047 (query->nar_hi << 8) + query->nar_lo);
1047 1048
1048 if (!(flags & 0x8000)) { 1049 if (!(flags & 0x8000)) {
2187 ngx_int_t event; 2188 ngx_int_t event;
2188 ngx_event_t *rev, *wev; 2189 ngx_event_t *rev, *wev;
2189 ngx_socket_t s; 2190 ngx_socket_t s;
2190 ngx_connection_t *c; 2191 ngx_connection_t *c;
2191 2192
2192 s = ngx_socket(AF_INET, SOCK_DGRAM, 0); 2193 s = ngx_socket(uc->sockaddr->sa_family, SOCK_DGRAM, 0);
2193 2194
2194 ngx_log_debug1(NGX_LOG_DEBUG_EVENT, &uc->log, 0, "UDP socket %d", s); 2195 ngx_log_debug1(NGX_LOG_DEBUG_EVENT, &uc->log, 0, "UDP socket %d", s);
2195 2196
2196 if (s == -1) { 2197 if (s == -1) {
2197 ngx_log_error(NGX_LOG_ALERT, &uc->log, ngx_socket_errno, 2198 ngx_log_error(NGX_LOG_ALERT, &uc->log, ngx_socket_errno,