905e40b8ca3fe0dfff3726a62488ac6a25cc1ead
[openwrt/staging/yousong.git] / package / network / services / dnsmasq / patches / 020-implement-RFC6842.patch
1 From 88a77a78ad27adc3ed87b7ee603643d26cb896ee Mon Sep 17 00:00:00 2001
2 From: Simon Kelley <simon@thekelleys.org.uk>
3 Date: Sat, 11 Feb 2017 17:02:02 +0000
4 Subject: [PATCH] Implement RFC-6842 (Client-ids in DHCP replies.)
5
6 ---
7 CHANGELOG | 5 ++++-
8 src/rfc2131.c | 33 ++++++++++++++++++++++-----------
9 2 files changed, 26 insertions(+), 12 deletions(-)
10
11 diff --git a/CHANGELOG b/CHANGELOG
12 index f7f5125..a4ee280 100644
13 --- a/CHANGELOG
14 +++ b/CHANGELOG
15 @@ -74,7 +74,10 @@ version 2.77
16 of "local addresses only" entries. Thanks to Hannu Nyman for
17 the patch.
18
19 -
20 + Implement RFC 6842. Thanks to Reddeiah Raju Konduru for
21 + pointing out that this was missing.
22 +
23 +
24 version 2.76
25 Include 0.0.0.0/8 in DNS rebind checks. This range
26 translates to hosts on the local network, or, at
27 diff --git a/src/rfc2131.c b/src/rfc2131.c
28 index 978c8dc..3e97402 100644
29 --- a/src/rfc2131.c
30 +++ b/src/rfc2131.c
31 @@ -38,7 +38,7 @@ static void log_packet(char *type, void *addr, unsigned char *ext_mac,
32 static unsigned char *option_find(struct dhcp_packet *mess, size_t size, int opt_type, int minsize);
33 static unsigned char *option_find1(unsigned char *p, unsigned char *end, int opt, int minsize);
34 static size_t dhcp_packet_size(struct dhcp_packet *mess, unsigned char *agent_id, unsigned char *real_end);
35 -static void clear_packet(struct dhcp_packet *mess, unsigned char *end);
36 +static void clear_packet(struct dhcp_packet *mess, unsigned char *end, unsigned int sz);
37 static int in_list(unsigned char *list, int opt);
38 static void do_options(struct dhcp_context *context,
39 struct dhcp_packet *mess,
40 @@ -611,7 +611,7 @@ size_t dhcp_reply(struct dhcp_context *context, char *iface_name, int int_index,
41 now);
42 lease_set_interface(lease, int_index, now);
43
44 - clear_packet(mess, end);
45 + clear_packet(mess, end, 0);
46 do_options(context, mess, end, NULL, hostname, get_domain(mess->yiaddr),
47 netid, subnet_addr, 0, 0, -1, NULL, vendor_class_len, now, 0xffffffff, 0);
48 }
49 @@ -814,7 +814,7 @@ size_t dhcp_reply(struct dhcp_context *context, char *iface_name, int int_index,
50 if (!service || !service->basename || !context)
51 return 0;
52
53 - clear_packet(mess, end);
54 + clear_packet(mess, end, sz);
55
56 mess->yiaddr = mess->ciaddr;
57 mess->ciaddr.s_addr = 0;
58 @@ -882,7 +882,7 @@ size_t dhcp_reply(struct dhcp_context *context, char *iface_name, int int_index,
59 mess->flags |= htons(0x8000); /* broadcast */
60 }
61
62 - clear_packet(mess, end);
63 + clear_packet(mess, end, sz);
64
65 /* Redirect EFI clients to port 4011 */
66 if (pxearch >= 6)
67 @@ -1062,7 +1062,7 @@ size_t dhcp_reply(struct dhcp_context *context, char *iface_name, int int_index,
68 log_packet("DHCPOFFER" , &mess->yiaddr, emac, emac_len, iface_name, NULL, NULL, mess->xid);
69
70 time = calc_time(context, config, option_find(mess, sz, OPTION_LEASE_TIME, 4));
71 - clear_packet(mess, end);
72 + clear_packet(mess, end, sz);
73 option_put(mess, end, OPTION_MESSAGE_TYPE, 1, DHCPOFFER);
74 option_put(mess, end, OPTION_SERVER_IDENTIFIER, INADDRSZ, ntohl(server_id(context, override, fallback).s_addr));
75 option_put(mess, end, OPTION_LEASE_TIME, 4, time);
76 @@ -1245,7 +1245,7 @@ size_t dhcp_reply(struct dhcp_context *context, char *iface_name, int int_index,
77 log_packet("DHCPNAK", &mess->yiaddr, emac, emac_len, iface_name, NULL, message, mess->xid);
78
79 mess->yiaddr.s_addr = 0;
80 - clear_packet(mess, end);
81 + clear_packet(mess, end, sz);
82 option_put(mess, end, OPTION_MESSAGE_TYPE, 1, DHCPNAK);
83 option_put(mess, end, OPTION_SERVER_IDENTIFIER, INADDRSZ, ntohl(server_id(context, override, fallback).s_addr));
84 option_put_string(mess, end, OPTION_MESSAGE, message, borken_opt);
85 @@ -1401,7 +1401,7 @@ size_t dhcp_reply(struct dhcp_context *context, char *iface_name, int int_index,
86
87 log_packet("DHCPACK", &mess->yiaddr, emac, emac_len, iface_name, hostname, NULL, mess->xid);
88
89 - clear_packet(mess, end);
90 + clear_packet(mess, end, sz);
91 option_put(mess, end, OPTION_MESSAGE_TYPE, 1, DHCPACK);
92 option_put(mess, end, OPTION_SERVER_IDENTIFIER, INADDRSZ, ntohl(server_id(context, override, fallback).s_addr));
93 option_put(mess, end, OPTION_LEASE_TIME, 4, time);
94 @@ -1452,7 +1452,7 @@ size_t dhcp_reply(struct dhcp_context *context, char *iface_name, int int_index,
95 override = lease->override;
96 }
97
98 - clear_packet(mess, end);
99 + clear_packet(mess, end, sz);
100 option_put(mess, end, OPTION_MESSAGE_TYPE, 1, DHCPACK);
101 option_put(mess, end, OPTION_SERVER_IDENTIFIER, INADDRSZ, ntohl(server_id(context, override, fallback).s_addr));
102
103 @@ -2180,12 +2180,23 @@ static struct dhcp_opt *pxe_opts(int pxe_arch, struct dhcp_netid *netid, struct
104
105 return ret;
106 }
107 -
108 -static void clear_packet(struct dhcp_packet *mess, unsigned char *end)
109 +
110 +static void clear_packet(struct dhcp_packet *mess, unsigned char *end, unsigned int sz)
111 {
112 + unsigned char *opt;
113 + unsigned int clid_tot = 0;
114 +
115 + /* If sz is non-zero, save any client-id option by copying it as the first
116 + option in the new packet */
117 + if (sz != 0 && (opt = option_find(mess, sz, OPTION_CLIENT_ID, 1)))
118 + {
119 + clid_tot = option_len(opt) + 2u;
120 + memmove(&mess->options[0] + sizeof(u32), opt, clid_tot);
121 + }
122 +
123 memset(mess->sname, 0, sizeof(mess->sname));
124 memset(mess->file, 0, sizeof(mess->file));
125 - memset(&mess->options[0] + sizeof(u32), 0, end - (&mess->options[0] + sizeof(u32)));
126 + memset(&mess->options[0] + sizeof(u32) + clid_tot, 0, end - (&mess->options[0] + sizeof(u32) + clid_tot));
127 mess->siaddr.s_addr = 0;
128 }
129
130 --
131 1.7.10.4
132