From af78c9a73fbf7fe5b4d9030934bbc74e012c33b5 Mon Sep 17 00:00:00 2001 From: Zbigniew Jędrzejewski-Szmek Date: Jun 27 2017 17:22:41 +0000 Subject: Fix an out-of-bounds write in systemd-resolved --- diff --git a/0076-test-resolved-packet-add-a-simple-test-for-our-alloc.patch b/0076-test-resolved-packet-add-a-simple-test-for-our-alloc.patch new file mode 100644 index 0000000..227075c --- /dev/null +++ b/0076-test-resolved-packet-add-a-simple-test-for-our-alloc.patch @@ -0,0 +1,111 @@ +From cc3e26e6de62c793ac869d219dd8aa7757249893 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Zbigniew=20J=C4=99drzejewski-Szmek?= +Date: Sun, 18 Jun 2017 15:53:15 -0400 +Subject: [PATCH 1/2] test-resolved-packet: add a simple test for our + allocation functions + +--- + .gitignore | 1 + + Makefile.am | 14 ++++++++++++ + src/resolve/test-resolved-packet.c | 45 ++++++++++++++++++++++++++++++++++++++ + 3 files changed, 60 insertions(+) + create mode 100644 src/resolve/test-resolved-packet.c + +diff --git a/.gitignore b/.gitignore +index 01cb6e7db7..25b976a0e3 100644 +--- a/.gitignore ++++ b/.gitignore +@@ -269,6 +269,7 @@ + /test-replace-var + /test-resolve + /test-resolve-tables ++/test-resolved-packet + /test-ring + /test-rlimit-util + /test-sched-prio +diff --git a/Makefile.am b/Makefile.am +index a767a5aa0d..e97a66e0fa 100644 +--- a/Makefile.am ++++ b/Makefile.am +@@ -5663,6 +5663,7 @@ dist_zshcompletion_data += \ + tests += \ + test-dns-packet \ + test-resolve-tables \ ++ test-resolved-packet \ + test-dnssec + + manual_tests += \ +@@ -5684,6 +5685,19 @@ test_resolve_tables_LDADD = \ + $(GCRYPT_LIBS) \ + -lm + ++test_resolved_packet_SOURCES = \ ++ src/resolve/test-resolved-packet.c \ ++ $(basic_dns_sources) ++ ++test_resolved_packet_CFLAGS = \ ++ $(AM_CFLAGS) \ ++ $(GCRYPT_CFLAGS) ++ ++test_resolved_packet_LDADD = \ ++ libsystemd-shared.la \ ++ $(GCRYPT_LIBS) \ ++ -lm ++ + test_dns_packet_SOURCES = \ + src/resolve/test-dns-packet.c \ + $(basic_dns_sources) +diff --git a/src/resolve/test-resolved-packet.c b/src/resolve/test-resolved-packet.c +new file mode 100644 +index 0000000000..8b7da1408d +--- /dev/null ++++ b/src/resolve/test-resolved-packet.c +@@ -0,0 +1,45 @@ ++/*** ++ This file is part of systemd ++ ++ Copyright 2017 Zbigniew Jędrzejewski-Szmek ++ ++ systemd is free software; you can redistribute it and/or modify it ++ under the terms of the GNU Lesser General Public License as published by ++ the Free Software Foundation; either version 2.1 of the License, or ++ (at your option) any later version. ++ ++ systemd is distributed in the hope that it will be useful, but ++ WITHOUT ANY WARRANTY; without even the implied warranty of ++ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU ++ Lesser General Public License for more details. ++ ++ You should have received a copy of the GNU Lesser General Public License ++ along with systemd; If not, see . ++***/ ++ ++#include "log.h" ++#include "resolved-dns-packet.h" ++ ++static void test_dns_packet_new(void) { ++ size_t i; ++ ++ for (i = 0; i < DNS_PACKET_SIZE_MAX + 2; i++) { ++ _cleanup_(dns_packet_unrefp) DnsPacket *p = NULL; ++ ++ assert_se(dns_packet_new(&p, DNS_PROTOCOL_DNS, i) == 0); ++ ++ log_debug("dns_packet_new: %zu → %zu", i, p->allocated); ++ assert_se(p->allocated >= MIN(DNS_PACKET_SIZE_MAX, i)); ++ } ++} ++ ++int main(int argc, char **argv) { ++ ++ log_set_max_level(LOG_DEBUG); ++ log_parse_environment(); ++ log_open(); ++ ++ test_dns_packet_new(); ++ ++ return 0; ++} +-- +2.13.0 + diff --git a/0077-resolved-simplify-alloc-size-calculation.patch b/0077-resolved-simplify-alloc-size-calculation.patch new file mode 100644 index 0000000..ba73087 --- /dev/null +++ b/0077-resolved-simplify-alloc-size-calculation.patch @@ -0,0 +1,51 @@ +From d2a286714f136404d05c8981a2e0820c1dd6e0a9 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Zbigniew=20J=C4=99drzejewski-Szmek?= +Date: Sun, 18 Jun 2017 16:07:57 -0400 +Subject: [PATCH 2/2] resolved: simplify alloc size calculation + +The allocation size was calculated in a complicated way, and for values +close to the page size we would actually allocate less than requested. + +Reported by Chris Coulson . + +CVE-2017-9445 +--- + src/resolve/resolved-dns-packet.c | 8 +------- + src/resolve/resolved-dns-packet.h | 2 -- + 2 files changed, 1 insertion(+), 9 deletions(-) + +diff --git a/src/resolve/resolved-dns-packet.c b/src/resolve/resolved-dns-packet.c +index 240ee448f4..821b66e266 100644 +--- a/src/resolve/resolved-dns-packet.c ++++ b/src/resolve/resolved-dns-packet.c +@@ -47,13 +47,7 @@ int dns_packet_new(DnsPacket **ret, DnsProtocol protocol, size_t mtu) { + + assert(ret); + +- if (mtu <= UDP_PACKET_HEADER_SIZE) +- a = DNS_PACKET_SIZE_START; +- else +- a = mtu - UDP_PACKET_HEADER_SIZE; +- +- if (a < DNS_PACKET_HEADER_SIZE) +- a = DNS_PACKET_HEADER_SIZE; ++ a = MAX(mtu, DNS_PACKET_HEADER_SIZE); + + /* round up to next page size */ + a = PAGE_ALIGN(ALIGN(sizeof(DnsPacket)) + a) - ALIGN(sizeof(DnsPacket)); +diff --git a/src/resolve/resolved-dns-packet.h b/src/resolve/resolved-dns-packet.h +index 2c92392e4d..3abcaf8cf3 100644 +--- a/src/resolve/resolved-dns-packet.h ++++ b/src/resolve/resolved-dns-packet.h +@@ -66,8 +66,6 @@ struct DnsPacketHeader { + /* With EDNS0 we can use larger packets, default to 4096, which is what is commonly used */ + #define DNS_PACKET_UNICAST_SIZE_LARGE_MAX 4096 + +-#define DNS_PACKET_SIZE_START 512 +- + struct DnsPacket { + int n_ref; + DnsProtocol protocol; +-- +2.13.0 + diff --git a/systemd.spec b/systemd.spec index 5807375..7f65954 100644 --- a/systemd.spec +++ b/systemd.spec @@ -13,7 +13,7 @@ Name: systemd Url: http://www.freedesktop.org/wiki/Software/systemd Version: 233 -Release: 4%{?gitcommit:.git%{gitcommitshort}}%{?dist} +Release: 5%{?gitcommit:.git%{gitcommitshort}}%{?dist} # For a breakdown of the licensing, see README License: LGPLv2+ and MIT and GPLv2+ Summary: System and Service Manager @@ -121,6 +121,9 @@ Patch0072: 0072-zsh-add-completion-for-add-wants-and-add-requires-60.patch Patch0073: 0073-udev-stop-freeing-value-after-using-it-for-setting-s.patch Patch0074: 0074-core-mount-pass-c-flag-to-bin-umount-6093.patch Patch0075: 0075-man-systemd-timesyncd.service-8-6109.patch +Patch0076: 0076-test-resolved-packet-add-a-simple-test-for-our-alloc.patch +Patch0077: 0077-resolved-simplify-alloc-size-calculation.patch + Source0990: hwdb.patch @@ -1121,6 +1124,9 @@ getent passwd systemd-journal-upload &>/dev/null || useradd -r -l -g systemd-jou %{pkgdir}/tests %changelog +* Tue Jun 27 2017 zbyszek - 233-5 +- Fix an out-of-bounds write in systemd-resolved (CVE-2017-9445) + * Thu Jun 15 2017 zbyszek - 233-4 - Backport a bunch of small fixes (memleaks, wrong format strings, man page clarifications, shell completion)