1*4882a593SmuzhiyunFrom 782a4580a5e347793443aa8e9152db1bf4a0fff8 Mon Sep 17 00:00:00 2001
2*4882a593SmuzhiyunFrom: Peter Jones <pjones@redhat.com>
3*4882a593SmuzhiyunDate: Mon, 15 Jun 2020 10:58:42 -0400
4*4882a593SmuzhiyunSubject: [PATCH] safemath: Add some arithmetic primitives that check for
5*4882a593Smuzhiyun overflow
6*4882a593SmuzhiyunMIME-Version: 1.0
7*4882a593SmuzhiyunContent-Type: text/plain; charset=UTF-8
8*4882a593SmuzhiyunContent-Transfer-Encoding: 8bit
9*4882a593Smuzhiyun
10*4882a593SmuzhiyunThis adds a new header, include/grub/safemath.h, that includes easy to
11*4882a593Smuzhiyunuse wrappers for __builtin_{add,sub,mul}_overflow() declared like:
12*4882a593Smuzhiyun
13*4882a593Smuzhiyun  bool OP(a, b, res)
14*4882a593Smuzhiyun
15*4882a593Smuzhiyunwhere OP is grub_add, grub_sub or grub_mul. OP() returns true in the
16*4882a593Smuzhiyuncase where the operation would overflow and res is not modified.
17*4882a593SmuzhiyunOtherwise, false is returned and the operation is executed.
18*4882a593Smuzhiyun
19*4882a593SmuzhiyunThese arithmetic primitives require newer compiler versions. So, bump
20*4882a593Smuzhiyunthese requirements in the INSTALL file too.
21*4882a593Smuzhiyun
22*4882a593SmuzhiyunSigned-off-by: Peter Jones <pjones@redhat.com>
23*4882a593SmuzhiyunReviewed-by: Daniel Kiper <daniel.kiper@oracle.com>
24*4882a593SmuzhiyunSigned-off-by: Stefan Sørensen <stefan.sorensen@spectralink.com>
25*4882a593Smuzhiyun---
26*4882a593Smuzhiyun INSTALL                 | 22 ++--------------------
27*4882a593Smuzhiyun include/grub/compiler.h |  8 ++++++++
28*4882a593Smuzhiyun include/grub/safemath.h | 37 +++++++++++++++++++++++++++++++++++++
29*4882a593Smuzhiyun 3 files changed, 47 insertions(+), 20 deletions(-)
30*4882a593Smuzhiyun create mode 100644 include/grub/safemath.h
31*4882a593Smuzhiyun
32*4882a593Smuzhiyundiff --git a/INSTALL b/INSTALL
33*4882a593Smuzhiyunindex 8acb40902..dcb9b7d7b 100644
34*4882a593Smuzhiyun--- a/INSTALL
35*4882a593Smuzhiyun+++ b/INSTALL
36*4882a593Smuzhiyun@@ -11,27 +11,9 @@ GRUB depends on some software packages installed into your system. If
37*4882a593Smuzhiyun you don't have any of them, please obtain and install them before
38*4882a593Smuzhiyun configuring the GRUB.
39*4882a593Smuzhiyun
40*4882a593Smuzhiyun-* GCC 4.1.3 or later
41*4882a593Smuzhiyun-  Note: older versions may work but support is limited
42*4882a593Smuzhiyun-
43*4882a593Smuzhiyun-  Experimental support for clang 3.3 or later (results in much bigger binaries)
44*4882a593Smuzhiyun+* GCC 5.1.0 or later
45*4882a593Smuzhiyun+  Experimental support for clang 3.8.0 or later (results in much bigger binaries)
46*4882a593Smuzhiyun   for i386, x86_64, arm (including thumb), arm64, mips(el), powerpc, sparc64
47*4882a593Smuzhiyun-  Note: clang 3.2 or later works for i386 and x86_64 targets but results in
48*4882a593Smuzhiyun-        much bigger binaries.
49*4882a593Smuzhiyun-	earlier versions not tested
50*4882a593Smuzhiyun-  Note: clang 3.2 or later works for arm
51*4882a593Smuzhiyun-	earlier versions not tested
52*4882a593Smuzhiyun-  Note: clang on arm64 is not supported due to
53*4882a593Smuzhiyun-	https://llvm.org/bugs/show_bug.cgi?id=26030
54*4882a593Smuzhiyun-  Note: clang 3.3 or later works for mips(el)
55*4882a593Smuzhiyun-	earlier versions fail to generate .reginfo and hence gprel relocations
56*4882a593Smuzhiyun-	fail.
57*4882a593Smuzhiyun-  Note: clang 3.2 or later works for powerpc
58*4882a593Smuzhiyun-	earlier versions not tested
59*4882a593Smuzhiyun-  Note: clang 3.5 or later works for sparc64
60*4882a593Smuzhiyun-        earlier versions return "error: unable to interface with target machine"
61*4882a593Smuzhiyun-  Note: clang has no support for ia64 and hence you can't compile GRUB
62*4882a593Smuzhiyun-	for ia64 with clang
63*4882a593Smuzhiyun * GNU Make
64*4882a593Smuzhiyun * GNU Bison 2.3 or later
65*4882a593Smuzhiyun * GNU gettext 0.17 or later
66*4882a593Smuzhiyundiff --git a/include/grub/compiler.h b/include/grub/compiler.h
67*4882a593Smuzhiyunindex c9e1d7a73..8f3be3ae7 100644
68*4882a593Smuzhiyun--- a/include/grub/compiler.h
69*4882a593Smuzhiyun+++ b/include/grub/compiler.h
70*4882a593Smuzhiyun@@ -48,4 +48,12 @@
71*4882a593Smuzhiyun #  define WARN_UNUSED_RESULT
72*4882a593Smuzhiyun #endif
73*4882a593Smuzhiyun
74*4882a593Smuzhiyun+#if defined(__clang__) && defined(__clang_major__) && defined(__clang_minor__)
75*4882a593Smuzhiyun+#  define CLANG_PREREQ(maj,min) \
76*4882a593Smuzhiyun+          ((__clang_major__ > (maj)) || \
77*4882a593Smuzhiyun+	   (__clang_major__ == (maj) && __clang_minor__ >= (min)))
78*4882a593Smuzhiyun+#else
79*4882a593Smuzhiyun+#  define CLANG_PREREQ(maj,min) 0
80*4882a593Smuzhiyun+#endif
81*4882a593Smuzhiyun+
82*4882a593Smuzhiyun #endif /* ! GRUB_COMPILER_HEADER */
83*4882a593Smuzhiyundiff --git a/include/grub/safemath.h b/include/grub/safemath.h
84*4882a593Smuzhiyunnew file mode 100644
85*4882a593Smuzhiyunindex 000000000..c17b89bba
86*4882a593Smuzhiyun--- /dev/null
87*4882a593Smuzhiyun+++ b/include/grub/safemath.h
88*4882a593Smuzhiyun@@ -0,0 +1,37 @@
89*4882a593Smuzhiyun+/*
90*4882a593Smuzhiyun+ *  GRUB  --  GRand Unified Bootloader
91*4882a593Smuzhiyun+ *  Copyright (C) 2020  Free Software Foundation, Inc.
92*4882a593Smuzhiyun+ *
93*4882a593Smuzhiyun+ *  GRUB is free software: you can redistribute it and/or modify
94*4882a593Smuzhiyun+ *  it under the terms of the GNU General Public License as published by
95*4882a593Smuzhiyun+ *  the Free Software Foundation, either version 3 of the License, or
96*4882a593Smuzhiyun+ *  (at your option) any later version.
97*4882a593Smuzhiyun+ *
98*4882a593Smuzhiyun+ *  GRUB is distributed in the hope that it will be useful,
99*4882a593Smuzhiyun+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
100*4882a593Smuzhiyun+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
101*4882a593Smuzhiyun+ *  GNU General Public License for more details.
102*4882a593Smuzhiyun+ *
103*4882a593Smuzhiyun+ *  You should have received a copy of the GNU General Public License
104*4882a593Smuzhiyun+ *  along with GRUB.  If not, see <http://www.gnu.org/licenses/>.
105*4882a593Smuzhiyun+ *
106*4882a593Smuzhiyun+ *  Arithmetic operations that protect against overflow.
107*4882a593Smuzhiyun+ */
108*4882a593Smuzhiyun+
109*4882a593Smuzhiyun+#ifndef GRUB_SAFEMATH_H
110*4882a593Smuzhiyun+#define GRUB_SAFEMATH_H 1
111*4882a593Smuzhiyun+
112*4882a593Smuzhiyun+#include <grub/compiler.h>
113*4882a593Smuzhiyun+
114*4882a593Smuzhiyun+/* These appear in gcc 5.1 and clang 3.8. */
115*4882a593Smuzhiyun+#if GNUC_PREREQ(5, 1) || CLANG_PREREQ(3, 8)
116*4882a593Smuzhiyun+
117*4882a593Smuzhiyun+#define grub_add(a, b, res)	__builtin_add_overflow(a, b, res)
118*4882a593Smuzhiyun+#define grub_sub(a, b, res)	__builtin_sub_overflow(a, b, res)
119*4882a593Smuzhiyun+#define grub_mul(a, b, res)	__builtin_mul_overflow(a, b, res)
120*4882a593Smuzhiyun+
121*4882a593Smuzhiyun+#else
122*4882a593Smuzhiyun+#error gcc 5.1 or newer or clang 3.8 or newer is required
123*4882a593Smuzhiyun+#endif
124*4882a593Smuzhiyun+
125*4882a593Smuzhiyun+#endif /* GRUB_SAFEMATH_H */
126*4882a593Smuzhiyun--
127*4882a593Smuzhiyun2.26.2
128*4882a593Smuzhiyun
129