Package: dhcp
Version: 2.0pl5-19.1

There is a bug in ISC DHCP server version 2 that causes the server to
unexpectedly exit when it receieves a DHCPOFFER packet with a
client-identifier option which is exactly 32 bytes long.

A malicious user could use this as a sort of denial of service attack on
a version 2 dhcp server.  This does not appear to be a problem with the
dhcp version 3 server.

Explanation of the bug:
The DHCP server has a lease struct which contains a buffer (uid_buf)
which is 32 bytes long.  If it needs more space, it simply malloc's new
storage.  There is an edge condition in supersede_lease() from memory.c
that causes a 32 byte client-identifier to be mistakenly interpreted as
a corrupt uid, and so the server exits with the message "corrupt lease
uid."

To reproduce:
You can use the dhclient included in the dhcp package.  Set up a "send
dhcp-client-identifier" directive to send a 32 byte client-identifier,
and then activate dhclient.  The dhcp server will exit as soon as it
recieves the DHCPDISCOVER packet.

More info:
This is not a stack overflow issue.  There does not seem to be any
possibility of remote compromise from this issue. 

Windows clients generally do not send client-identifier options greater
than 6 bytes, but it looks like Mac OS X uses a longer string.  That is
how we originally noticed the issue.

The short patch below resolves the issue.

Andrew Steets
Wayport Software Engineering
[EMAIL PROTECTED]
(512) 519-6061


*** common/memory.c     1999-05-27 12:47:43.000000000 -0500
--- ../fixed/dhcp-2.0pl5/common/memory.c        2006-07-28 14:25:32.796953968 
-0500
***************
*** 528,534 ****
                /* Copy the data files, but not the linkages. */
                comp -> starts = lease -> starts;
                if (lease -> uid) {
!                       if (lease -> uid_len < sizeof (lease -> uid_buf)) {
                                memcpy (comp -> uid_buf,
                                        lease -> uid, lease -> uid_len);
                                comp -> uid = &comp -> uid_buf [0];
--- 528,534 ----
                /* Copy the data files, but not the linkages. */
                comp -> starts = lease -> starts;
                if (lease -> uid) {
!                       if (lease -> uid_len <= sizeof (lease -> uid_buf)) {
                                memcpy (comp -> uid_buf,
                                        lease -> uid, lease -> uid_len);
                                comp -> uid = &comp -> uid_buf [0];




-- 
To UNSUBSCRIBE, email to [EMAIL PROTECTED]
with a subject of "unsubscribe". Trouble? Contact [EMAIL PROTECTED]

Reply via email to