Fix crash if upstream server returns SERVFAIL when
--conntrack in use. Thanks to Giacomo Tazzari for finding
this and supplying the patch.
+
+ Repair regression in 2.64. That release stopped sending
+ lease-time information in the reply to DHCPINFORM
+ requests, on the correct grounds that it was a standards
+ violation. However, this broke the dnsmasq-specific
+ dhcp_lease_time utility. Now, DHCPINFORM returns
+ lease-time only if it's specifically requested
+ (maintaining standards) and the dhcp_lease_time utility
+ has been taught to ask for it (restoring functionality).
version 2.66
nothing is sent to stdout a message is sent to stderr and a
non-zero error code is returned.
- Requires dnsmasq 2.40 or later.
+ This version requires dnsmasq 2.67 or later.
*/
#include <sys/types.h>
#define OPTION_LEASE_TIME 51
#define OPTION_OVERLOAD 52
#define OPTION_MESSAGE_TYPE 53
+#define OPTION_REQUESTED_OPTIONS 55
#define OPTION_END 255
#define DHCPINFORM 8
#define DHCP_SERVER_PORT 67
*(p++) = 1;
*(p++) = DHCPINFORM;
+ /* Explicity request the lease time, it won't be sent otherwise:
+ this is a dnsmasq extension, not standard. */
+ *(p++) = OPTION_REQUESTED_OPTIONS;
+ *(p++) = 1;
+ *(p++) = OPTION_LEASE_TIME;
+
*(p++) = OPTION_END;
dest.sin_family = AF_INET;
static unsigned char *option_find1(unsigned char *p, unsigned char *end, int opt, int minsize);
static size_t dhcp_packet_size(struct dhcp_packet *mess, unsigned char *agent_id, unsigned char *real_end);
static void clear_packet(struct dhcp_packet *mess, unsigned char *end);
+static int in_list(unsigned char *list, int opt);
static void do_options(struct dhcp_context *context,
struct dhcp_packet *mess,
unsigned char *real_end,
clear_packet(mess, end);
option_put(mess, end, OPTION_MESSAGE_TYPE, 1, DHCPACK);
option_put(mess, end, OPTION_SERVER_IDENTIFIER, INADDRSZ, ntohl(server_id(context, override, fallback).s_addr));
-
+
+ /* RFC 2131 says that DHCPINFORM shouldn't include lease-time parameters, but
+ we supply a utility which makes DHCPINFORM requests to get this information.
+ Only include lease time if OPTION_LEASE_TIME is in the parameter request list,
+ which won't be true for ordinary clients, but will be true for the
+ dhcp_lease_time utility. */
+ if (lease && in_list(req_options, OPTION_LEASE_TIME))
+ {
+ if (lease->expires == 0)
+ time = 0xffffffff;
+ else
+ time = (unsigned int)difftime(lease->expires, now);
+ option_put(mess, end, OPTION_LEASE_TIME, 4, time);
+ }
+
do_options(context, mess, end, req_options, hostname, get_domain(mess->ciaddr),
netid, subnet_addr, fqdn_flags, borken_opt, pxearch, uuid, vendor_class_len, now);