fixed bug #37705 Possible memory corruption in DNS query

This commit is contained in:
Simon Goldschmidt 2013-01-14 18:03:23 +01:00
parent 769b2a3e30
commit d12600fba0
2 changed files with 19 additions and 6 deletions

View File

@ -80,6 +80,9 @@ HISTORY
++ Bugfixes: ++ Bugfixes:
2013-01-14: Simon Goldschmidt
* dns.c: fixed bug #37705 Possible memory corruption in DNS query
2013-01-11: Simon Goldschmidt 2013-01-11: Simon Goldschmidt
* raw.c: fixed bug #38066 Raw pcbs can alter packet without eating it * raw.c: fixed bug #38066 Raw pcbs can alter packet without eating it

View File

@ -576,6 +576,7 @@ dns_send(u8_t numdns, const char* name, u8_t id)
p = pbuf_alloc(PBUF_TRANSPORT, SIZEOF_DNS_HDR + DNS_MAX_NAME_LENGTH + p = pbuf_alloc(PBUF_TRANSPORT, SIZEOF_DNS_HDR + DNS_MAX_NAME_LENGTH +
SIZEOF_DNS_QUERY, PBUF_RAM); SIZEOF_DNS_QUERY, PBUF_RAM);
if (p != NULL) { if (p != NULL) {
u16_t realloc_size;
LWIP_ASSERT("pbuf must be in one piece", p->next == NULL); LWIP_ASSERT("pbuf must be in one piece", p->next == NULL);
/* fill dns header */ /* fill dns header */
hdr = (struct dns_hdr*)p->payload; hdr = (struct dns_hdr*)p->payload;
@ -607,7 +608,9 @@ dns_send(u8_t numdns, const char* name, u8_t id)
SMEMCPY(query, &qry, SIZEOF_DNS_QUERY); SMEMCPY(query, &qry, SIZEOF_DNS_QUERY);
/* resize pbuf to the exact dns query */ /* resize pbuf to the exact dns query */
pbuf_realloc(p, (u16_t)((query + SIZEOF_DNS_QUERY) - ((char*)(p->payload)))); realloc_size = (u16_t)((query + SIZEOF_DNS_QUERY) - ((char*)(p->payload)));
LWIP_ASSERT("p->tot_len >= realloc_size", p->tot_len >= realloc_size);
pbuf_realloc(p, realloc_size);
/* connect to the server for faster receiving */ /* connect to the server for faster receiving */
udp_connect(dns_pcb, &dns_servers[numdns], DNS_SERVER_PORT); udp_connect(dns_pcb, &dns_servers[numdns], DNS_SERVER_PORT);
@ -860,12 +863,14 @@ memerr:
* Queues a new hostname to resolve and sends out a DNS query for that hostname * Queues a new hostname to resolve and sends out a DNS query for that hostname
* *
* @param name the hostname that is to be queried * @param name the hostname that is to be queried
* @param hostnamelen length of the hostname
* @param found a callback founction to be called on success, failure or timeout * @param found a callback founction to be called on success, failure or timeout
* @param callback_arg argument to pass to the callback function * @param callback_arg argument to pass to the callback function
* @return @return a err_t return code. * @return @return a err_t return code.
*/ */
static err_t static err_t
dns_enqueue(const char *name, dns_found_callback found, void *callback_arg) dns_enqueue(const char *name, size_t hostnamelen, dns_found_callback found,
void *callback_arg)
{ {
u8_t i; u8_t i;
u8_t lseq, lseqi; u8_t lseq, lseqi;
@ -910,7 +915,7 @@ dns_enqueue(const char *name, dns_found_callback found, void *callback_arg)
pEntry->seqno = dns_seqno++; pEntry->seqno = dns_seqno++;
pEntry->found = found; pEntry->found = found;
pEntry->arg = callback_arg; pEntry->arg = callback_arg;
namelen = LWIP_MIN(strlen(name), DNS_MAX_NAME_LENGTH-1); namelen = LWIP_MIN(hostnamelen, DNS_MAX_NAME_LENGTH-1);
MEMCPY(pEntry->name, name, namelen); MEMCPY(pEntry->name, name, namelen);
pEntry->name[namelen] = 0; pEntry->name[namelen] = 0;
@ -945,13 +950,18 @@ dns_gethostbyname(const char *hostname, ip_addr_t *addr, dns_found_callback foun
void *callback_arg) void *callback_arg)
{ {
u32_t ipaddr; u32_t ipaddr;
size_t hostnamelen;
/* not initialized or no valid server yet, or invalid addr pointer /* not initialized or no valid server yet, or invalid addr pointer
* or invalid hostname or invalid hostname length */ * or invalid hostname or invalid hostname length */
if ((dns_pcb == NULL) || (addr == NULL) || if ((dns_pcb == NULL) || (addr == NULL) ||
(!hostname) || (!hostname[0]) || (!hostname) || (!hostname[0])) {
(strlen(hostname) >= DNS_MAX_NAME_LENGTH)) {
return ERR_ARG; return ERR_ARG;
} }
hostnamelen = strlen(hostname);
if (hostnamelen >= DNS_MAX_NAME_LENGTH) {
return ERR_ARG;
}
#if LWIP_HAVE_LOOPIF #if LWIP_HAVE_LOOPIF
if (strcmp(hostname, "localhost")==0) { if (strcmp(hostname, "localhost")==0) {
@ -972,7 +982,7 @@ dns_gethostbyname(const char *hostname, ip_addr_t *addr, dns_found_callback foun
} }
/* queue query with specified callback */ /* queue query with specified callback */
return dns_enqueue(hostname, found, callback_arg); return dns_enqueue(hostname, hostnamelen, found, callback_arg);
} }
#endif /* LWIP_DNS */ #endif /* LWIP_DNS */