mailing list archives
Fix for stack overflow in dns.lua
From: David Fifield <david () bamsoftware com>
Date: Wed, 19 Nov 2008 13:41:35 -0700
I found that a function in dns.lua could recurse infinitely (until it
overflowed the stack) when given a specially crafted message. DNS
message can employ a kind of compression as described in section 4.1.4
of RFC 1035. A message may end with a pointer to another index in the
message; the decoder follows the pointer to get the rest of the message.
When the function dns.decStr finds a pointer in a message it calls
itself to recursively get the rest of the message. If the pointer is set
up so as to create a loop, the function calls itself until the stack
You can reproduce the crash before r11129 with the file dns.bytes
(attached). Its hexadecimal contents are
1234 8180 0001 0000 0000 0000 C00C
The C00C is a pointer that points to itself. You can feed this data to
dns.lua by setting up a fake DNS server with Ncat:
ncat -u -l localhost 53 < dns.bytes
nmap -d -sP --script=asn-query.nse --script-args dns=localhost scanme.nmap.org
The script output will be
SCRIPT ENGINE: Initiating script scanning.
SCRIPT ENGINE: Script scanning scanme.nmap.org (188.8.131.52).
SCRIPT ENGINE: Initialized 1 rules
SCRIPT ENGINE: Matching rules.
SCRIPT ENGINE: Will run /usr/share/nmap/scripts/asn-query.nse against 184.108.40.206
SCRIPT ENGINE: Running scripts.
SCRIPT ENGINE: Runlevel: 1.000000
Initiating SCRIPT ENGINE at 15:34
SCRIPT ENGINE: /usr/share/nmap/nselib/dns.lua:486: stack overflow
Completed SCRIPT ENGINE at 15:34, 0.09s elapsed
SCRIPT ENGINE: Script scanning completed.
Looping a pointer to itself isn't the only way to do this. A pointer
could refer to itself minus a few bytes, or two pointers could link to
I fixed the problem by setting a limit on the number of pointers to
follow--currently set at 1. This is still more capable than
advance_past_dns_name in nmap_dns.cc, which follows only one pointer and
only if it's the very first thing in the message (if I understand the
code correctly). djbdns uses a limit of 1000; see dns_packet.c. That
seems excessive for our UDP packets which will usually be much smaller
than 512 bytes.
I was made aware of this class of vulnerability by my former professor
Steve Beaty. Here are some more links on it.
Sent through the nmap-dev mailing list
Archived at http://SecLists.Org
- Fix for stack overflow in dns.lua David Fifield (Nov 19)