summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorArmin Kuster <akuster@mvista.com>2018-08-07 21:00:50 -0700
committerRichard Purdie <richard.purdie@linuxfoundation.org>2018-08-15 10:22:45 +0100
commit4e970e640940fe59afda9ce9b3a28cf72d0d6b6c (patch)
treebfcf8b6e5e5094a5c08f24d7dd590bdd377eab97
parentad4d04429ac4f8b19f04b4c439ee6e815e699136 (diff)
downloadpoky-4e970e640940fe59afda9ce9b3a28cf72d0d6b6c.tar.gz
Binutils: Security fix for CVE-2017-17121
Affects: <= 2.29.1 (From OE-Core rev: 942e7f65fd656f2cc526a3c99edcea60f341132c) Signed-off-by: Armin Kuster <akuster@mvista.com> Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
-rw-r--r--meta/recipes-devtools/binutils/binutils-2.29.1.inc1
-rw-r--r--meta/recipes-devtools/binutils/binutils/CVE-2017-17121.patch366
2 files changed, 367 insertions, 0 deletions
diff --git a/meta/recipes-devtools/binutils/binutils-2.29.1.inc b/meta/recipes-devtools/binutils/binutils-2.29.1.inc
index 2a713caf5d..27d77cc409 100644
--- a/meta/recipes-devtools/binutils/binutils-2.29.1.inc
+++ b/meta/recipes-devtools/binutils/binutils-2.29.1.inc
@@ -61,6 +61,7 @@ SRC_URI = "\
61 file://CVE-2017-16831.patch \ 61 file://CVE-2017-16831.patch \
62 file://CVE-2017-16832.patch \ 62 file://CVE-2017-16832.patch \
63 file://CVE-2017-17080.patch \ 63 file://CVE-2017-17080.patch \
64 file://CVE-2017-17121.patch \
64" 65"
65S = "${WORKDIR}/git" 66S = "${WORKDIR}/git"
66 67
diff --git a/meta/recipes-devtools/binutils/binutils/CVE-2017-17121.patch b/meta/recipes-devtools/binutils/binutils/CVE-2017-17121.patch
new file mode 100644
index 0000000000..4b675f7b72
--- /dev/null
+++ b/meta/recipes-devtools/binutils/binutils/CVE-2017-17121.patch
@@ -0,0 +1,366 @@
1From b23dc97fe237a1d9e850d7cbeee066183a00630b Mon Sep 17 00:00:00 2001
2From: Nick Clifton <nickc@redhat.com>
3Date: Tue, 28 Nov 2017 13:20:31 +0000
4Subject: [PATCH] Fix a memory access violation when attempting to parse a
5 corrupt COFF binary with a relocation that points beyond the end of the
6 section to be relocated.
7
8 PR 22506
9 * reloc.c (reloc_offset_in_range): Rename to
10 bfd_reloc_offset_in_range and export.
11 (bfd_perform_relocation): Rename function invocation.
12 (bfd_install_relocation): Likewise.
13 (bfd_final_link_relocate): Likewise.
14 * bfd-in2.h: Regenerate.
15 * coff-arm.c (coff_arm_reloc): Use bfd_reloc_offset_in_range.
16 * coff-i386.c (coff_i386_reloc): Likewise.
17 * coff-i860.c (coff_i860_reloc): Likewise.
18 * coff-m68k.c (mk68kcoff_common_addend_special_fn): Likewise.
19 * coff-m88k.c (m88k_special_reloc): Likewise.
20 * coff-mips.c (mips_reflo_reloc): Likewise.
21 * coff-x86_64.c (coff_amd64_reloc): Likewise.
22
23Upstream-Status: Backport
24Affects: <= 2.29.1
25CVE: CVE-2017-17121
26Signed-off-by: Armin Kuster <akuster@mvista.com>
27
28---
29 bfd/ChangeLog | 17 +++++++++++++++
30 bfd/bfd-in2.h | 6 +++++
31 bfd/coff-arm.c | 65 ++++++++++++++++++++++++++++++-------------------------
32 bfd/coff-i386.c | 5 +++++
33 bfd/coff-i860.c | 5 +++++
34 bfd/coff-m68k.c | 5 +++++
35 bfd/coff-m88k.c | 9 +++++++-
36 bfd/coff-mips.c | 6 +++++
37 bfd/coff-x86_64.c | 16 +++++---------
38 bfd/reloc.c | 40 +++++++++++++++++++++++++++++-----
39 10 files changed, 126 insertions(+), 48 deletions(-)
40
41Index: git/bfd/bfd-in2.h
42===================================================================
43--- git.orig/bfd/bfd-in2.h
44+++ git/bfd/bfd-in2.h
45@@ -2661,6 +2661,12 @@ bfd_reloc_status_type bfd_check_overflow
46 unsigned int addrsize,
47 bfd_vma relocation);
48
49+bfd_boolean bfd_reloc_offset_in_range
50+ (reloc_howto_type *howto,
51+ bfd *abfd,
52+ asection *section,
53+ bfd_size_type offset);
54+
55 bfd_reloc_status_type bfd_perform_relocation
56 (bfd *abfd,
57 arelent *reloc_entry,
58Index: git/bfd/coff-arm.c
59===================================================================
60--- git.orig/bfd/coff-arm.c
61+++ git/bfd/coff-arm.c
62@@ -109,41 +109,46 @@ coff_arm_reloc (bfd *abfd,
63 x = ((x & ~howto->dst_mask) \
64 | (((x & howto->src_mask) + diff) & howto->dst_mask))
65
66- if (diff != 0)
67- {
68- reloc_howto_type *howto = reloc_entry->howto;
69- unsigned char *addr = (unsigned char *) data + reloc_entry->address;
70+ if (diff != 0)
71+ {
72+ reloc_howto_type *howto = reloc_entry->howto;
73+ unsigned char *addr = (unsigned char *) data + reloc_entry->address;
74+
75+ if (! bfd_reloc_offset_in_range (howto, abfd, input_section,
76+ reloc_entry->address
77+ * bfd_octets_per_byte (abfd)))
78+ return bfd_reloc_outofrange;
79+
80+ switch (howto->size)
81+ {
82+ case 0:
83+ {
84+ char x = bfd_get_8 (abfd, addr);
85+ DOIT (x);
86+ bfd_put_8 (abfd, x, addr);
87+ }
88+ break;
89
90- switch (howto->size)
91+ case 1:
92 {
93- case 0:
94- {
95- char x = bfd_get_8 (abfd, addr);
96- DOIT (x);
97- bfd_put_8 (abfd, x, addr);
98- }
99- break;
100-
101- case 1:
102- {
103- short x = bfd_get_16 (abfd, addr);
104- DOIT (x);
105- bfd_put_16 (abfd, (bfd_vma) x, addr);
106- }
107- break;
108-
109- case 2:
110- {
111- long x = bfd_get_32 (abfd, addr);
112- DOIT (x);
113- bfd_put_32 (abfd, (bfd_vma) x, addr);
114- }
115- break;
116+ short x = bfd_get_16 (abfd, addr);
117+ DOIT (x);
118+ bfd_put_16 (abfd, (bfd_vma) x, addr);
119+ }
120+ break;
121
122- default:
123- abort ();
124+ case 2:
125+ {
126+ long x = bfd_get_32 (abfd, addr);
127+ DOIT (x);
128+ bfd_put_32 (abfd, (bfd_vma) x, addr);
129 }
130- }
131+ break;
132+
133+ default:
134+ abort ();
135+ }
136+ }
137
138 /* Now let bfd_perform_relocation finish everything up. */
139 return bfd_reloc_continue;
140Index: git/bfd/coff-i386.c
141===================================================================
142--- git.orig/bfd/coff-i386.c
143+++ git/bfd/coff-i386.c
144@@ -144,6 +144,11 @@ coff_i386_reloc (bfd *abfd,
145 reloc_howto_type *howto = reloc_entry->howto;
146 unsigned char *addr = (unsigned char *) data + reloc_entry->address;
147
148+ if (! bfd_reloc_offset_in_range (howto, abfd, input_section,
149+ reloc_entry->address
150+ * bfd_octets_per_byte (abfd)))
151+ return bfd_reloc_outofrange;
152+
153 switch (howto->size)
154 {
155 case 0:
156Index: git/bfd/coff-i860.c
157===================================================================
158--- git.orig/bfd/coff-i860.c
159+++ git/bfd/coff-i860.c
160@@ -95,6 +95,11 @@ coff_i860_reloc (bfd *abfd,
161 reloc_howto_type *howto = reloc_entry->howto;
162 unsigned char *addr = (unsigned char *) data + reloc_entry->address;
163
164+ if (! bfd_reloc_offset_in_range (howto, abfd, input_section,
165+ reloc_entry->address
166+ * bfd_octets_per_byte (abfd)))
167+ return bfd_reloc_outofrange;
168+
169 switch (howto->size)
170 {
171 case 0:
172Index: git/bfd/coff-m68k.c
173===================================================================
174--- git.orig/bfd/coff-m68k.c
175+++ git/bfd/coff-m68k.c
176@@ -305,6 +305,11 @@ m68kcoff_common_addend_special_fn (bfd *
177 reloc_howto_type *howto = reloc_entry->howto;
178 unsigned char *addr = (unsigned char *) data + reloc_entry->address;
179
180+ if (! bfd_reloc_offset_in_range (howto, abfd, input_section,
181+ reloc_entry->address
182+ * bfd_octets_per_byte (abfd)))
183+ return bfd_reloc_outofrange;
184+
185 switch (howto->size)
186 {
187 case 0:
188Index: git/bfd/coff-m88k.c
189===================================================================
190--- git.orig/bfd/coff-m88k.c
191+++ git/bfd/coff-m88k.c
192@@ -72,10 +72,17 @@ m88k_special_reloc (bfd *abfd,
193 {
194 bfd_vma output_base = 0;
195 bfd_vma addr = reloc_entry->address;
196- bfd_vma x = bfd_get_16 (abfd, (bfd_byte *) data + addr);
197+ bfd_vma x;
198 asection *reloc_target_output_section;
199 long relocation = 0;
200
201+ if (! bfd_reloc_offset_in_range (howto, abfd, input_section,
202+ reloc_entry->address
203+ * bfd_octets_per_byte (abfd)))
204+ return bfd_reloc_outofrange;
205+
206+ x = bfd_get_16 (abfd, (bfd_byte *) data + addr);
207+
208 /* Work out which section the relocation is targeted at and the
209 initial relocation command value. */
210
211Index: git/bfd/coff-mips.c
212===================================================================
213--- git.orig/bfd/coff-mips.c
214+++ git/bfd/coff-mips.c
215@@ -504,6 +504,12 @@ mips_reflo_reloc (bfd *abfd ATTRIBUTE_UN
216 unsigned long vallo;
217 struct mips_hi *next;
218
219+ if (! bfd_reloc_offset_in_range (reloc_entry->howto, abfd,
220+ input_section,
221+ reloc_entry->address
222+ * bfd_octets_per_byte (abfd)))
223+ return bfd_reloc_outofrange;
224+
225 /* Do the REFHI relocation. Note that we actually don't
226 need to know anything about the REFLO itself, except
227 where to find the low 16 bits of the addend needed by the
228Index: git/bfd/coff-x86_64.c
229===================================================================
230--- git.orig/bfd/coff-x86_64.c
231+++ git/bfd/coff-x86_64.c
232@@ -143,16 +143,10 @@ coff_amd64_reloc (bfd *abfd,
233 reloc_howto_type *howto = reloc_entry->howto;
234 unsigned char *addr = (unsigned char *) data + reloc_entry->address;
235
236- /* FIXME: We do not have an end address for data, so we cannot
237- accurately range check any addresses computed against it.
238- cf: PR binutils/17512: file: 1085-1761-0.004.
239- For now we do the best that we can. */
240- if (addr < (unsigned char *) data
241- || addr > ((unsigned char *) data) + input_section->size)
242- {
243- bfd_set_error (bfd_error_bad_value);
244- return bfd_reloc_notsupported;
245- }
246+ if (! bfd_reloc_offset_in_range (howto, abfd, input_section,
247+ reloc_entry->address
248+ * bfd_octets_per_byte (abfd)))
249+ return bfd_reloc_outofrange;
250
251 switch (howto->size)
252 {
253Index: git/bfd/reloc.c
254===================================================================
255--- git.orig/bfd/reloc.c
256+++ git/bfd/reloc.c
257@@ -538,12 +538,31 @@ bfd_check_overflow (enum complain_overfl
258 return flag;
259 }
260
261+/*
262+FUNCTION
263+ bfd_reloc_offset_in_range
264+
265+SYNOPSIS
266+ bfd_boolean bfd_reloc_offset_in_range
267+ (reloc_howto_type *howto,
268+ bfd *abfd,
269+ asection *section,
270+ bfd_size_type offset);
271+
272+DESCRIPTION
273+ Returns TRUE if the reloc described by @var{HOWTO} can be
274+ applied at @var{OFFSET} octets in @var{SECTION}.
275+
276+*/
277+
278 /* HOWTO describes a relocation, at offset OCTET. Return whether the
279 relocation field is within SECTION of ABFD. */
280
281-static bfd_boolean
282-reloc_offset_in_range (reloc_howto_type *howto, bfd *abfd,
283- asection *section, bfd_size_type octet)
284+bfd_boolean
285+bfd_reloc_offset_in_range (reloc_howto_type *howto,
286+ bfd *abfd,
287+ asection *section,
288+ bfd_size_type octet)
289 {
290 bfd_size_type octet_end = bfd_get_section_limit_octets (abfd, section);
291 bfd_size_type reloc_size = bfd_get_reloc_size (howto);
292@@ -617,6 +636,11 @@ bfd_perform_relocation (bfd *abfd,
293 if (howto && howto->special_function)
294 {
295 bfd_reloc_status_type cont;
296+
297+ /* Note - we do not call bfd_reloc_offset_in_range here as the
298+ reloc_entry->address field might actually be valid for the
299+ backend concerned. It is up to the special_function itself
300+ to call bfd_reloc_offset_in_range if needed. */
301 cont = howto->special_function (abfd, reloc_entry, symbol, data,
302 input_section, output_bfd,
303 error_message);
304@@ -637,7 +661,7 @@ bfd_perform_relocation (bfd *abfd,
305
306 /* Is the address of the relocation really within the section? */
307 octets = reloc_entry->address * bfd_octets_per_byte (abfd);
308- if (!reloc_offset_in_range (howto, abfd, input_section, octets))
309+ if (!bfd_reloc_offset_in_range (howto, abfd, input_section, octets))
310 return bfd_reloc_outofrange;
311
312 /* Work out which section the relocation is targeted at and the
313@@ -1003,6 +1027,10 @@ bfd_install_relocation (bfd *abfd,
314 {
315 bfd_reloc_status_type cont;
316
317+ /* Note - we do not call bfd_reloc_offset_in_range here as the
318+ reloc_entry->address field might actually be valid for the
319+ backend concerned. It is up to the special_function itself
320+ to call bfd_reloc_offset_in_range if needed. */
321 /* XXX - The special_function calls haven't been fixed up to deal
322 with creating new relocations and section contents. */
323 cont = howto->special_function (abfd, reloc_entry, symbol,
324@@ -1025,7 +1053,7 @@ bfd_install_relocation (bfd *abfd,
325
326 /* Is the address of the relocation really within the section? */
327 octets = reloc_entry->address * bfd_octets_per_byte (abfd);
328- if (!reloc_offset_in_range (howto, abfd, input_section, octets))
329+ if (!bfd_reloc_offset_in_range (howto, abfd, input_section, octets))
330 return bfd_reloc_outofrange;
331
332 /* Work out which section the relocation is targeted at and the
333@@ -1363,7 +1391,7 @@ _bfd_final_link_relocate (reloc_howto_ty
334 bfd_size_type octets = address * bfd_octets_per_byte (input_bfd);
335
336 /* Sanity check the address. */
337- if (!reloc_offset_in_range (howto, input_bfd, input_section, octets))
338+ if (!bfd_reloc_offset_in_range (howto, input_bfd, input_section, octets))
339 return bfd_reloc_outofrange;
340
341 /* This function assumes that we are dealing with a basic relocation
342Index: git/bfd/ChangeLog
343===================================================================
344--- git.orig/bfd/ChangeLog
345+++ git/bfd/ChangeLog
346@@ -1,3 +1,20 @@
347+2017-11-28 Nick Clifton <nickc@redhat.com>
348+
349+ PR 22506
350+ * reloc.c (reloc_offset_in_range): Rename to
351+ bfd_reloc_offset_in_range and export.
352+ (bfd_perform_relocation): Rename function invocation.
353+ (bfd_install_relocation): Likewise.
354+ (bfd_final_link_relocate): Likewise.
355+ * bfd-in2.h: Regenerate.
356+ * coff-arm.c (coff_arm_reloc): Use bfd_reloc_offset_in_range.
357+ * coff-i386.c (coff_i386_reloc): Likewise.
358+ * coff-i860.c (coff_i860_reloc): Likewise.
359+ * coff-m68k.c (mk68kcoff_common_addend_special_fn): Likewise.
360+ * coff-m88k.c (m88k_special_reloc): Likewise.
361+ * coff-mips.c (mips_reflo_reloc): Likewise.
362+ * coff-x86_64.c (coff_amd64_reloc): Likewise.
363+
364 2017-11-16 Nick Clifton <nickc@redhat.com>
365
366 PR 22421