- Rebase to 2.79
- Stop using nettle_hashes directly, use access function (#1548060) - Do not break on cname with spaces (#1498667) Signed-off-by: Petr Menšík <pemensik@redhat.com>
This commit is contained in:
parent
144c414c67
commit
1f9c5b6ea6
1
.gitignore
vendored
1
.gitignore
vendored
@ -26,3 +26,4 @@ dnsmasq-2.52.tar.lzma
|
||||
/dnsmasq-2.77rc2.tar.xz
|
||||
/dnsmasq-2.77.tar.xz
|
||||
/dnsmasq-2.78.tar.xz
|
||||
/dnsmasq-2.79.tar.xz
|
||||
|
@ -1,4 +1,4 @@
|
||||
From 9d2757b9714523b53ed487b57e740f1b5beb4e0b Mon Sep 17 00:00:00 2001
|
||||
From c82a594d95431e8615126621397ea595eb037a6b Mon Sep 17 00:00:00 2001
|
||||
From: Doran Moppert <dmoppert@redhat.com>
|
||||
Date: Tue, 26 Sep 2017 14:48:20 +0930
|
||||
Subject: [PATCH] google patch hand-applied
|
||||
@ -6,11 +6,11 @@ Subject: [PATCH] google patch hand-applied
|
||||
---
|
||||
src/edns0.c | 10 +++++-----
|
||||
src/forward.c | 4 ++++
|
||||
src/rfc1035.c | 6 ++++--
|
||||
3 files changed, 13 insertions(+), 7 deletions(-)
|
||||
src/rfc1035.c | 2 ++
|
||||
3 files changed, 11 insertions(+), 5 deletions(-)
|
||||
|
||||
diff --git a/src/edns0.c b/src/edns0.c
|
||||
index 9c6dbcb..268fbe7 100644
|
||||
index af33877..ba6ff0c 100644
|
||||
--- a/src/edns0.c
|
||||
+++ b/src/edns0.c
|
||||
@@ -212,11 +212,11 @@ size_t add_pseudoheader(struct dns_header *header, size_t plen, unsigned char *l
|
||||
@ -31,10 +31,10 @@ index 9c6dbcb..268fbe7 100644
|
||||
free(buff);
|
||||
p += rdlen;
|
||||
diff --git a/src/forward.c b/src/forward.c
|
||||
index d1962be..6b9c16e 100644
|
||||
index cdd11d3..3078f64 100644
|
||||
--- a/src/forward.c
|
||||
+++ b/src/forward.c
|
||||
@@ -1417,6 +1417,10 @@ void receive_query(struct listener *listen, time_t now)
|
||||
@@ -1438,6 +1438,10 @@ void receive_query(struct listener *listen, time_t now)
|
||||
udp_size = PACKETSZ; /* Sanity check - can't reduce below default. RFC 6891 6.2.3 */
|
||||
}
|
||||
|
||||
@ -46,21 +46,10 @@ index d1962be..6b9c16e 100644
|
||||
if (auth_dns)
|
||||
{
|
||||
diff --git a/src/rfc1035.c b/src/rfc1035.c
|
||||
index 0bf3bcc..3513455 100644
|
||||
index b078b59..777911b 100644
|
||||
--- a/src/rfc1035.c
|
||||
+++ b/src/rfc1035.c
|
||||
@@ -1198,8 +1198,8 @@ int add_resource_record(struct dns_header *header, char *limit, int *truncp, int
|
||||
va_end(ap); /* clean up variable argument pointer */
|
||||
|
||||
j = p - sav - 2;
|
||||
- /* this has already been checked against limit before */
|
||||
- PUTSHORT(j, sav); /* Now, store real RDLength */
|
||||
+ /* this has already been checked against limit before */
|
||||
+ PUTSHORT(j, sav); /* Now, store real RDLength */
|
||||
|
||||
/* check for overflow of buffer */
|
||||
if (limit && ((unsigned char *)limit - p) < 0)
|
||||
@@ -1259,6 +1259,8 @@ size_t answer_request(struct dns_header *header, char *limit, size_t qlen,
|
||||
@@ -1281,6 +1281,8 @@ size_t answer_request(struct dns_header *header, char *limit, size_t qlen,
|
||||
int nxdomain = 0, auth = 1, trunc = 0, sec_data = 1;
|
||||
struct mx_srv_record *rec;
|
||||
size_t len;
|
||||
@ -70,5 +59,5 @@ index 0bf3bcc..3513455 100644
|
||||
if (ntohs(header->ancount) != 0 ||
|
||||
ntohs(header->nscount) != 0 ||
|
||||
--
|
||||
2.9.5
|
||||
2.14.3
|
||||
|
||||
|
@ -1,212 +0,0 @@
|
||||
From 7dcf32a822eeaf134526660f8c2826e18f0a8c83 Mon Sep 17 00:00:00 2001
|
||||
From: Simon Kelley <simon@thekelleys.org.uk>
|
||||
Date: Fri, 19 Jan 2018 12:26:08 +0000
|
||||
Subject: [PATCH] DNSSEC fix for wildcard NSEC records. CVE-2017-15107 applies.
|
||||
|
||||
It's OK for NSEC records to be expanded from wildcards,
|
||||
but in that case, the proof of non-existence is only valid
|
||||
starting at the wildcard name, *.<domain> NOT the name expanded
|
||||
from the wildcard. Without this check it's possible for an
|
||||
attacker to craft an NSEC which wrongly proves non-existence
|
||||
in a domain which includes a wildcard for NSEC.
|
||||
|
||||
(cherry picked from commit 4fe6744a220eddd3f1749b40cac3dfc510787de6)
|
||||
|
||||
Fix DNSSEC validation errors introduced in 4fe6744a220eddd3f1749b40cac3dfc510787de6
|
||||
|
||||
(cherry picked from commit cd7df612b14ec1bf831a966ccaf076be0dae7404)
|
||||
---
|
||||
src/dnssec.c | 117 ++++++++++++++++++++++++++++++++++++++++++++++++++++-------
|
||||
1 file changed, 103 insertions(+), 14 deletions(-)
|
||||
|
||||
diff --git a/src/dnssec.c b/src/dnssec.c
|
||||
index a74d01a..704f03f 100644
|
||||
--- a/src/dnssec.c
|
||||
+++ b/src/dnssec.c
|
||||
@@ -424,15 +424,17 @@ static void from_wire(char *name)
|
||||
static int count_labels(char *name)
|
||||
{
|
||||
int i;
|
||||
-
|
||||
+ char *p;
|
||||
+
|
||||
if (*name == 0)
|
||||
return 0;
|
||||
|
||||
- for (i = 0; *name; name++)
|
||||
- if (*name == '.')
|
||||
+ for (p = name, i = 0; *p; p++)
|
||||
+ if (*p == '.')
|
||||
i++;
|
||||
|
||||
- return i+1;
|
||||
+ /* Don't count empty first label. */
|
||||
+ return *name == '.' ? i : i+1;
|
||||
}
|
||||
|
||||
/* Implement RFC1982 wrapped compare for 32-bit numbers */
|
||||
@@ -1405,8 +1407,8 @@ static int hostname_cmp(const char *a, const char *b)
|
||||
}
|
||||
}
|
||||
|
||||
-static int prove_non_existence_nsec(struct dns_header *header, size_t plen, unsigned char **nsecs, int nsec_count,
|
||||
- char *workspace1, char *workspace2, char *name, int type, int *nons)
|
||||
+static int prove_non_existence_nsec(struct dns_header *header, size_t plen, unsigned char **nsecs, unsigned char **labels, int nsec_count,
|
||||
+ char *workspace1_in, char *workspace2, char *name, int type, int *nons)
|
||||
{
|
||||
int i, rc, rdlen;
|
||||
unsigned char *p, *psave;
|
||||
@@ -1419,6 +1421,9 @@ static int prove_non_existence_nsec(struct dns_header *header, size_t plen, unsi
|
||||
/* Find NSEC record that proves name doesn't exist */
|
||||
for (i = 0; i < nsec_count; i++)
|
||||
{
|
||||
+ char *workspace1 = workspace1_in;
|
||||
+ int sig_labels, name_labels;
|
||||
+
|
||||
p = nsecs[i];
|
||||
if (!extract_name(header, plen, &p, workspace1, 1, 10))
|
||||
return 0;
|
||||
@@ -1427,7 +1432,27 @@ static int prove_non_existence_nsec(struct dns_header *header, size_t plen, unsi
|
||||
psave = p;
|
||||
if (!extract_name(header, plen, &p, workspace2, 1, 10))
|
||||
return 0;
|
||||
-
|
||||
+
|
||||
+ /* If NSEC comes from wildcard expansion, use original wildcard
|
||||
+ as name for computation. */
|
||||
+ sig_labels = *labels[i];
|
||||
+ name_labels = count_labels(workspace1);
|
||||
+
|
||||
+ if (sig_labels < name_labels)
|
||||
+ {
|
||||
+ int k;
|
||||
+ for (k = name_labels - sig_labels; k != 0; k--)
|
||||
+ {
|
||||
+ while (*workspace1 != '.' && *workspace1 != 0)
|
||||
+ workspace1++;
|
||||
+ if (k != 1 && *workspace1 == '.')
|
||||
+ workspace1++;
|
||||
+ }
|
||||
+
|
||||
+ workspace1--;
|
||||
+ *workspace1 = '*';
|
||||
+ }
|
||||
+
|
||||
rc = hostname_cmp(workspace1, name);
|
||||
|
||||
if (rc == 0)
|
||||
@@ -1825,24 +1850,26 @@ static int prove_non_existence_nsec3(struct dns_header *header, size_t plen, uns
|
||||
|
||||
static int prove_non_existence(struct dns_header *header, size_t plen, char *keyname, char *name, int qtype, int qclass, char *wildname, int *nons)
|
||||
{
|
||||
- static unsigned char **nsecset = NULL;
|
||||
- static int nsecset_sz = 0;
|
||||
+ static unsigned char **nsecset = NULL, **rrsig_labels = NULL;
|
||||
+ static int nsecset_sz = 0, rrsig_labels_sz = 0;
|
||||
|
||||
int type_found = 0;
|
||||
- unsigned char *p = skip_questions(header, plen);
|
||||
+ unsigned char *auth_start, *p = skip_questions(header, plen);
|
||||
int type, class, rdlen, i, nsecs_found;
|
||||
|
||||
/* Move to NS section */
|
||||
if (!p || !(p = skip_section(p, ntohs(header->ancount), header, plen)))
|
||||
return 0;
|
||||
+
|
||||
+ auth_start = p;
|
||||
|
||||
for (nsecs_found = 0, i = ntohs(header->nscount); i != 0; i--)
|
||||
{
|
||||
unsigned char *pstart = p;
|
||||
|
||||
- if (!(p = skip_name(p, header, plen, 10)))
|
||||
+ if (!extract_name(header, plen, &p, daemon->workspacename, 1, 10))
|
||||
return 0;
|
||||
-
|
||||
+
|
||||
GETSHORT(type, p);
|
||||
GETSHORT(class, p);
|
||||
p += 4; /* TTL */
|
||||
@@ -1859,7 +1886,69 @@ static int prove_non_existence(struct dns_header *header, size_t plen, char *key
|
||||
if (!expand_workspace(&nsecset, &nsecset_sz, nsecs_found))
|
||||
return 0;
|
||||
|
||||
- nsecset[nsecs_found++] = pstart;
|
||||
+ if (type == T_NSEC)
|
||||
+ {
|
||||
+ /* If we're looking for NSECs, find the corresponding SIGs, to
|
||||
+ extract the labels value, which we need in case the NSECs
|
||||
+ are the result of wildcard expansion.
|
||||
+ Note that the NSEC may not have been validated yet
|
||||
+ so if there are multiple SIGs, make sure the label value
|
||||
+ is the same in all, to avoid be duped by a rogue one.
|
||||
+ If there are no SIGs, that's an error */
|
||||
+ unsigned char *p1 = auth_start;
|
||||
+ int res, j, rdlen1, type1, class1;
|
||||
+
|
||||
+ if (!expand_workspace(&rrsig_labels, &rrsig_labels_sz, nsecs_found))
|
||||
+ return 0;
|
||||
+
|
||||
+ rrsig_labels[nsecs_found] = NULL;
|
||||
+
|
||||
+ for (j = ntohs(header->nscount); j != 0; j--)
|
||||
+ {
|
||||
+ if (!(res = extract_name(header, plen, &p1, daemon->workspacename, 0, 10)))
|
||||
+ return 0;
|
||||
+
|
||||
+ GETSHORT(type1, p1);
|
||||
+ GETSHORT(class1, p1);
|
||||
+ p1 += 4; /* TTL */
|
||||
+ GETSHORT(rdlen1, p1);
|
||||
+
|
||||
+ if (!CHECK_LEN(header, p1, plen, rdlen1))
|
||||
+ return 0;
|
||||
+
|
||||
+ if (res == 1 && class1 == qclass && type1 == T_RRSIG)
|
||||
+ {
|
||||
+ int type_covered;
|
||||
+ unsigned char *psav = p1;
|
||||
+
|
||||
+ if (rdlen1 < 18)
|
||||
+ return 0; /* bad packet */
|
||||
+
|
||||
+ GETSHORT(type_covered, p1);
|
||||
+
|
||||
+ if (type_covered == T_NSEC)
|
||||
+ {
|
||||
+ p1++; /* algo */
|
||||
+
|
||||
+ /* labels field must be the same in every SIG we find. */
|
||||
+ if (!rrsig_labels[nsecs_found])
|
||||
+ rrsig_labels[nsecs_found] = p1;
|
||||
+ else if (*rrsig_labels[nsecs_found] != *p1) /* algo */
|
||||
+ return 0;
|
||||
+ }
|
||||
+ p1 = psav;
|
||||
+ }
|
||||
+
|
||||
+ if (!ADD_RDLEN(header, p1, plen, rdlen1))
|
||||
+ return 0;
|
||||
+ }
|
||||
+
|
||||
+ /* Must have found at least one sig. */
|
||||
+ if (!rrsig_labels[nsecs_found])
|
||||
+ return 0;
|
||||
+ }
|
||||
+
|
||||
+ nsecset[nsecs_found++] = pstart;
|
||||
}
|
||||
|
||||
if (!ADD_RDLEN(header, p, plen, rdlen))
|
||||
@@ -1867,7 +1956,7 @@ static int prove_non_existence(struct dns_header *header, size_t plen, char *key
|
||||
}
|
||||
|
||||
if (type_found == T_NSEC)
|
||||
- return prove_non_existence_nsec(header, plen, nsecset, nsecs_found, daemon->workspacename, keyname, name, qtype, nons);
|
||||
+ return prove_non_existence_nsec(header, plen, nsecset, rrsig_labels, nsecs_found, daemon->workspacename, keyname, name, qtype, nons);
|
||||
else if (type_found == T_NSEC3)
|
||||
return prove_non_existence_nsec3(header, plen, nsecset, nsecs_found, daemon->workspacename, keyname, name, qtype, wildname, nons);
|
||||
else
|
||||
--
|
||||
2.14.3
|
||||
|
11
dnsmasq.spec
11
dnsmasq.spec
@ -12,8 +12,8 @@
|
||||
%define _hardened_build 1
|
||||
|
||||
Name: dnsmasq
|
||||
Version: 2.78
|
||||
Release: 7%{?extraversion:.%{extraversion}}%{?dist}
|
||||
Version: 2.79
|
||||
Release: 1%{?extraversion:.%{extraversion}}%{?dist}
|
||||
Summary: A lightweight DHCP/caching DNS server
|
||||
|
||||
License: GPLv2 or GPLv3
|
||||
@ -24,7 +24,6 @@ Source2: dnsmasq-systemd-sysusers.conf
|
||||
|
||||
# https://bugzilla.redhat.com/show_bug.cgi?id=1495409
|
||||
Patch1: dnsmasq-2.77-underflow.patch
|
||||
Patch2: dnsmasq-2.78-CVE-2017-15107.patch
|
||||
Patch3: dnsmasq-2.78-fips.patch
|
||||
|
||||
|
||||
@ -58,7 +57,6 @@ server's leases.
|
||||
%prep
|
||||
%setup -q -n %{name}-%{version}%{?extraversion}
|
||||
%patch1 -p1 -b .underflow
|
||||
%patch2 -p1 -b .CVE-2017-15107
|
||||
%patch3 -p1 -b .fips
|
||||
|
||||
# use /var/lib/dnsmasq instead of /var/lib/misc
|
||||
@ -159,6 +157,11 @@ install -Dpm 644 %{SOURCE2} %{buildroot}%{_sysusersdir}/dnsmasq.conf
|
||||
%{_mandir}/man1/dhcp_*
|
||||
|
||||
%changelog
|
||||
* Thu Mar 15 2018 Petr Menšík <pemensik@redhat.com> - 2.79-1
|
||||
- Rebase to 2.79
|
||||
- Stop using nettle_hashes directly, use access function (#1548060)
|
||||
- Do not break on cname with spaces (#1498667)
|
||||
|
||||
* Fri Mar 02 2018 Petr Menšík <pemensik@redhat.com> - 2.78-7
|
||||
- Emit warning with dnssec enabled on FIPS system (#1549507)
|
||||
|
||||
|
2
sources
2
sources
@ -1 +1 @@
|
||||
SHA512 (dnsmasq-2.78.tar.xz) = 9b79b84e5a768d52f90f6335ccef2c404ecd7a13e78e49f4cd0755fffc6cf34d0dc96ad4c72cad1dab3c5743a8d0d789b3e9b6e625b03c5675bb898ca61a698b
|
||||
SHA512 (dnsmasq-2.79.tar.xz) = 2c06212696ab55e1584f6133872f5b196013509e4b1822d0457787b456e14341afdde887749e370a2e512124cb4138f012f4601b08690707be4acc7cf2f2876f
|
||||
|
Loading…
Reference in New Issue
Block a user