From f3622ccbf95d7d1c6f31637a264989a20eda1374 Mon Sep 17 00:00:00 2001 From: Ken Raeburn Date: Thu, 5 Jun 2003 20:05:37 +0000 Subject: [PATCH] * locate_kdc.c (make_srv_query_realm): Punt if strdup fails. Always return what data we can, even if memory allocation or other problems prevent us from returning more. (krb5_locate_srv_dns_1): Always return what data we can. Fix memory leak. Free up temporary storage as quickly as possible, while building up address list to return. ticket: 1549 status: open git-svn-id: svn://anonsvn.mit.edu/krb5/trunk@15574 dc483132-0cff-0310-8789-dd5450dbe970 --- src/lib/krb5/os/ChangeLog | 9 +++++++ src/lib/krb5/os/locate_kdc.c | 49 ++++++++++++++++++------------------ 2 files changed, 34 insertions(+), 24 deletions(-) diff --git a/src/lib/krb5/os/ChangeLog b/src/lib/krb5/os/ChangeLog index 2ce37e88f..81c205665 100644 --- a/src/lib/krb5/os/ChangeLog +++ b/src/lib/krb5/os/ChangeLog @@ -1,3 +1,12 @@ +2003-06-05 Ken Raeburn + + * locate_kdc.c (make_srv_query_realm): Punt if strdup fails. + Always return what data we can, even if memory allocation or other + problems prevent us from returning more. + (krb5_locate_srv_dns_1): Always return what data we can. Fix + memory leak. Free up temporary storage as quickly as possible, + while building up address list to return. + 2003-06-03 Ken Raeburn * accessor.c (krb5int_accessor): Initialize restored locate_server diff --git a/src/lib/krb5/os/locate_kdc.c b/src/lib/krb5/os/locate_kdc.c index 6aaa98018..804dc7aae 100644 --- a/src/lib/krb5/os/locate_kdc.c +++ b/src/lib/krb5/os/locate_kdc.c @@ -516,6 +516,11 @@ struct srv_dns_entry { char *host; }; +/* Do DNS SRV query, return results in *answers. + + Make best effort to return all the data we can. On memory or + decoding errors, just return what we've got. Always return 0, + currently. */ static krb5_error_code make_srv_query_realm(const krb5_data *realm, const char *service, @@ -535,7 +540,6 @@ make_srv_query_realm(const krb5_data *realm, struct srv_dns_entry *head = NULL; struct srv_dns_entry *srv = NULL, *entry = NULL; - krb5_error_code code = 0; /* * First off, build a query of the form: @@ -548,7 +552,6 @@ make_srv_query_realm(const krb5_data *realm, * */ - *answers = 0; if (memchr(realm->data, 0, realm->length)) return 0; if ( strlen(service) + strlen(protocol) + realm->length + 6 @@ -683,6 +686,10 @@ make_srv_query_realm(const krb5_data *realm, srv->weight = weight; srv->port = port; srv->host = strdup(host); + if (srv->host == NULL) { + free(srv); + goto out; + } if (head == NULL || head->priority > srv->priority) { srv->next = head; @@ -708,10 +715,9 @@ make_srv_query_realm(const krb5_data *realm, INCR_CHECK(p, rdlen); } - *answers = head; - out: - return code; + *answers = head; + return 0; } static krb5_error_code @@ -722,23 +728,12 @@ krb5_locate_srv_dns_1 (const krb5_data *realm, int family) { struct srv_dns_entry *head = NULL; - struct srv_dns_entry *entry = NULL; + struct srv_dns_entry *entry = NULL, *next; krb5_error_code code = 0; - /* - * First off, build a query of the form: - * - * service.protocol.realm - * - * which will most likely be something like: - * - * _kerberos._udp.REALM - * - */ - code = make_srv_query_realm(realm, service, protocol, &head); if (code) - goto out; + return 0; /* * Okay! Now we've got a linked list of entries sorted by @@ -747,34 +742,40 @@ krb5_locate_srv_dns_1 (const krb5_data *realm, */ if (head == NULL) - goto out; + return 0; /* Check for the "." case indicating no support. */ if (head->next == 0 && head->host[0] == 0) { - code = KRB5_ERR_NO_SERVICE; - goto out; + free(head->host); + free(head); + return KRB5_ERR_NO_SERVICE; } #ifdef TEST fprintf (stderr, "walking answer list:\n"); #endif - for (entry = head; entry != NULL; entry = entry->next) { + for (entry = head; entry != NULL; entry = next) { #ifdef TEST fprintf (stderr, "\tport=%d host=%s\n", entry->port, entry->host); #endif + next = entry->next; code = add_host_to_list (addrlist, entry->host, htons (entry->port), 0, (strcmp("_tcp", protocol) ? SOCK_DGRAM : SOCK_STREAM), family); if (code) break; + if (entry == head) { + free(entry->host); + free(entry); + head = next; + entry = 0; + } } #ifdef TEST fprintf (stderr, "[end]\n"); #endif - out: - for (entry = head; entry != NULL; ) { struct srv_dns_entry *srv; free(entry->host); -- 2.26.2