diff options
Diffstat (limited to 'gnu/packages/patches')
-rw-r--r-- | gnu/packages/patches/cpio-gets-undeclared.patch | 45 | ||||
-rw-r--r-- | gnu/packages/patches/gsl-test-i686.patch | 17 | ||||
-rw-r--r-- | gnu/packages/patches/libx11-CVE-2016-7942.patch | 76 | ||||
-rw-r--r-- | gnu/packages/patches/libx11-CVE-2016-7943.patch | 113 | ||||
-rw-r--r-- | gnu/packages/patches/libxfixes-CVE-2016-7944.patch | 62 | ||||
-rw-r--r-- | gnu/packages/patches/libxi-CVE-2016-7945-CVE-2016-7946.patch | 420 | ||||
-rw-r--r-- | gnu/packages/patches/libxrandr-CVE-2016-7947-CVE-2016-7948.patch | 447 | ||||
-rw-r--r-- | gnu/packages/patches/libxrender-CVE-2016-7949.patch | 66 | ||||
-rw-r--r-- | gnu/packages/patches/libxrender-CVE-2016-7950.patch | 73 | ||||
-rw-r--r-- | gnu/packages/patches/libxtst-CVE-2016-7951-CVE-2016-7952.patch | 152 | ||||
-rw-r--r-- | gnu/packages/patches/libxv-CVE-2016-5407.patch | 162 | ||||
-rw-r--r-- | gnu/packages/patches/libxvmc-CVE-2016-7953.patch | 42 | ||||
-rw-r--r-- | gnu/packages/patches/metabat-remove-compilation-date.patch | 16 | ||||
-rw-r--r-- | gnu/packages/patches/rush-CVE-2013-6889.patch | 23 |
14 files changed, 1646 insertions, 68 deletions
diff --git a/gnu/packages/patches/cpio-gets-undeclared.patch b/gnu/packages/patches/cpio-gets-undeclared.patch deleted file mode 100644 index bc34de6455..0000000000 --- a/gnu/packages/patches/cpio-gets-undeclared.patch +++ /dev/null @@ -1,45 +0,0 @@ -This patch is needed to allow builds with newer versions of -the GNU libc (2.16+). - -The upstream fix was: - - commit 66712c23388e93e5c518ebc8515140fa0c807348 - Author: Eric Blake <eblake@redhat.com> - Date: Thu Mar 29 13:30:41 2012 -0600 - - stdio: don't assume gets any more - - Gnulib intentionally does not have a gets module, and now that C11 - and glibc have dropped it, we should be more proactive about warning - any user on a platform that still has a declaration of this dangerous - interface. - - * m4/stdio_h.m4 (gl_STDIO_H, gl_STDIO_H_DEFAULTS): Drop gets - support. - * modules/stdio (Makefile.am): Likewise. - * lib/stdio-read.c (gets): Likewise. - * tests/test-stdio-c++.cc: Likewise. - * m4/warn-on-use.m4 (gl_WARN_ON_USE_PREPARE): Fix comment. - * lib/stdio.in.h (gets): Make warning occur in more places. - * doc/posix-functions/gets.texi (gets): Update documentation. - Reported by Christer Solskogen. - - Signed-off-by: Eric Blake <eblake@redhat.com> - -This patch just gets rid of the offending part. - ---- cpio-2.11/gnu/stdio.in.h-orig 2012-11-25 22:17:06.000000000 +0400 -+++ cpio-2.11/gnu/stdio.in.h 2012-11-25 22:18:36.000000000 +0400 -@@ -135,12 +135,6 @@ - "use gnulib module fflush for portable POSIX compliance"); - #endif - --/* It is very rare that the developer ever has full control of stdin, -- so any use of gets warrants an unconditional warning. Assume it is -- always declared, since it is required by C89. */ --#undef gets --_GL_WARN_ON_USE (gets, "gets is a security hole - use fgets instead"); -- - #if @GNULIB_FOPEN@ - # if @REPLACE_FOPEN@ - # if !(defined __cplusplus && defined GNULIB_NAMESPACE) diff --git a/gnu/packages/patches/gsl-test-i686.patch b/gnu/packages/patches/gsl-test-i686.patch new file mode 100644 index 0000000000..8828c08614 --- /dev/null +++ b/gnu/packages/patches/gsl-test-i686.patch @@ -0,0 +1,17 @@ +Work around a test failure due to a rounding issue on 32-bit +platforms, as reported at: + + https://lists.gnu.org/archive/html/bug-gsl/2016-10/msg00000.html + +--- gsl-2.2.1/linalg/test.c 2016-10-05 13:27:42.464059730 +0200 ++++ gsl-2.2.1/linalg/test.c 2016-10-05 13:27:46.988095882 +0200 +@@ -4843,9 +4843,6 @@ main(void) + gsl_test(test_cholesky_decomp_unit(), "Cholesky Decomposition [unit triangular]"); + gsl_test(test_cholesky_solve(), "Cholesky Solve"); + +- gsl_test(test_cholesky_decomp(r), "Cholesky Decomposition"); +- gsl_test(test_cholesky_invert(r), "Cholesky Inverse"); +- gsl_test(test_pcholesky_decomp(r), "Pivoted Cholesky Decomposition"); + gsl_test(test_pcholesky_solve(r), "Pivoted Cholesky Solve"); + gsl_test(test_pcholesky_invert(r), "Pivoted Cholesky Inverse"); + gsl_test(test_mcholesky_decomp(r), "Modified Cholesky Decomposition"); diff --git a/gnu/packages/patches/libx11-CVE-2016-7942.patch b/gnu/packages/patches/libx11-CVE-2016-7942.patch new file mode 100644 index 0000000000..75770235ef --- /dev/null +++ b/gnu/packages/patches/libx11-CVE-2016-7942.patch @@ -0,0 +1,76 @@ +Fix CVE-2016-7942: + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7942 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libX11/commit/?id=8ea762f94f4c942d898fdeb590a1630c83235c17 + +From 8ea762f94f4c942d898fdeb590a1630c83235c17 Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 21:25:25 +0200 +Subject: [PATCH] Validation of server responses in XGetImage() + +Check if enough bytes were received for specified image type and +geometry. Otherwise GetPixel and other functions could trigger an +out of boundary read later on. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/GetImage.c | 29 ++++++++++++++++++++--------- + 1 file changed, 20 insertions(+), 9 deletions(-) + +diff --git a/src/GetImage.c b/src/GetImage.c +index c461abc..ff32d58 100644 +--- a/src/GetImage.c ++++ b/src/GetImage.c +@@ -59,6 +59,7 @@ XImage *XGetImage ( + char *data; + unsigned long nbytes; + XImage *image; ++ int planes; + LockDisplay(dpy); + GetReq (GetImage, req); + /* +@@ -91,18 +92,28 @@ XImage *XGetImage ( + return (XImage *) NULL; + } + _XReadPad (dpy, data, nbytes); +- if (format == XYPixmap) +- image = XCreateImage(dpy, _XVIDtoVisual(dpy, rep.visual), +- Ones (plane_mask & +- (((unsigned long)0xFFFFFFFF) >> (32 - rep.depth))), +- format, 0, data, width, height, dpy->bitmap_pad, 0); +- else /* format == ZPixmap */ +- image = XCreateImage (dpy, _XVIDtoVisual(dpy, rep.visual), +- rep.depth, ZPixmap, 0, data, width, height, +- _XGetScanlinePad(dpy, (int) rep.depth), 0); ++ if (format == XYPixmap) { ++ image = XCreateImage(dpy, _XVIDtoVisual(dpy, rep.visual), ++ Ones (plane_mask & ++ (((unsigned long)0xFFFFFFFF) >> (32 - rep.depth))), ++ format, 0, data, width, height, dpy->bitmap_pad, 0); ++ planes = image->depth; ++ } else { /* format == ZPixmap */ ++ image = XCreateImage (dpy, _XVIDtoVisual(dpy, rep.visual), ++ rep.depth, ZPixmap, 0, data, width, height, ++ _XGetScanlinePad(dpy, (int) rep.depth), 0); ++ planes = 1; ++ } + + if (!image) + Xfree(data); ++ if (planes < 1 || image->height < 1 || image->bytes_per_line < 1 || ++ INT_MAX / image->height <= image->bytes_per_line || ++ INT_MAX / planes <= image->height * image->bytes_per_line || ++ nbytes < planes * image->height * image->bytes_per_line) { ++ XDestroyImage(image); ++ image = NULL; ++ } + UnlockDisplay(dpy); + SyncHandle(); + return (image); +-- +2.10.1 + diff --git a/gnu/packages/patches/libx11-CVE-2016-7943.patch b/gnu/packages/patches/libx11-CVE-2016-7943.patch new file mode 100644 index 0000000000..7bcbc58dd4 --- /dev/null +++ b/gnu/packages/patches/libx11-CVE-2016-7943.patch @@ -0,0 +1,113 @@ +Fix CVE-2016-7943: + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7943. + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libX11/commit/?id=8c29f1607a31dac0911e45a0dd3d74173822b3c9 + +From 8c29f1607a31dac0911e45a0dd3d74173822b3c9 Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 21:22:57 +0200 +Subject: [PATCH] The validation of server responses avoids out of boundary + accesses. + +v2: FontNames.c return a NULL list whenever a single +length field from the server is incohent. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/FontNames.c | 23 +++++++++++++++++------ + src/ListExt.c | 12 ++++++++---- + src/ModMap.c | 3 ++- + 3 files changed, 27 insertions(+), 11 deletions(-) + +diff --git a/src/FontNames.c b/src/FontNames.c +index 21dcafe..e55f338 100644 +--- a/src/FontNames.c ++++ b/src/FontNames.c +@@ -66,7 +66,7 @@ int *actualCount) /* RETURN */ + + if (rep.nFonts) { + flist = Xmalloc (rep.nFonts * sizeof(char *)); +- if (rep.length < (INT_MAX >> 2)) { ++ if (rep.length > 0 && rep.length < (INT_MAX >> 2)) { + rlen = rep.length << 2; + ch = Xmalloc(rlen + 1); + /* +1 to leave room for last null-terminator */ +@@ -93,11 +93,22 @@ int *actualCount) /* RETURN */ + if (ch + length < chend) { + flist[i] = ch + 1; /* skip over length */ + ch += length + 1; /* find next length ... */ +- length = *(unsigned char *)ch; +- *ch = '\0'; /* and replace with null-termination */ +- count++; +- } else +- flist[i] = NULL; ++ if (ch <= chend) { ++ length = *(unsigned char *)ch; ++ *ch = '\0'; /* and replace with null-termination */ ++ count++; ++ } else { ++ Xfree(flist); ++ flist = NULL; ++ count = 0; ++ break; ++ } ++ } else { ++ Xfree(flist); ++ flist = NULL; ++ count = 0; ++ break; ++ } + } + } + *actualCount = count; +diff --git a/src/ListExt.c b/src/ListExt.c +index be6b989..0516e45 100644 +--- a/src/ListExt.c ++++ b/src/ListExt.c +@@ -55,7 +55,7 @@ char **XListExtensions( + + if (rep.nExtensions) { + list = Xmalloc (rep.nExtensions * sizeof (char *)); +- if (rep.length < (INT_MAX >> 2)) { ++ if (rep.length > 0 && rep.length < (INT_MAX >> 2)) { + rlen = rep.length << 2; + ch = Xmalloc (rlen + 1); + /* +1 to leave room for last null-terminator */ +@@ -80,9 +80,13 @@ char **XListExtensions( + if (ch + length < chend) { + list[i] = ch+1; /* skip over length */ + ch += length + 1; /* find next length ... */ +- length = *ch; +- *ch = '\0'; /* and replace with null-termination */ +- count++; ++ if (ch <= chend) { ++ length = *ch; ++ *ch = '\0'; /* and replace with null-termination */ ++ count++; ++ } else { ++ list[i] = NULL; ++ } + } else + list[i] = NULL; + } +diff --git a/src/ModMap.c b/src/ModMap.c +index a809aa2..49a5d08 100644 +--- a/src/ModMap.c ++++ b/src/ModMap.c +@@ -42,7 +42,8 @@ XGetModifierMapping(register Display *dpy) + GetEmptyReq(GetModifierMapping, req); + (void) _XReply (dpy, (xReply *)&rep, 0, xFalse); + +- if (rep.length < (INT_MAX >> 2)) { ++ if (rep.length < (INT_MAX >> 2) && ++ (rep.length >> 1) == rep.numKeyPerModifier) { + nbytes = (unsigned long)rep.length << 2; + res = Xmalloc(sizeof (XModifierKeymap)); + if (res) +-- +2.10.1 + diff --git a/gnu/packages/patches/libxfixes-CVE-2016-7944.patch b/gnu/packages/patches/libxfixes-CVE-2016-7944.patch new file mode 100644 index 0000000000..2ce463fc46 --- /dev/null +++ b/gnu/packages/patches/libxfixes-CVE-2016-7944.patch @@ -0,0 +1,62 @@ +Fix CVE-2016-7944: + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7944 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libXfixes/commit/?id=61c1039ee23a2d1de712843bed3480654d7ef42e + +From 61c1039ee23a2d1de712843bed3480654d7ef42e Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 22:38:44 +0200 +Subject: [PATCH] Integer overflow on illegal server response + +The 32 bit field "rep.length" is not checked for validity, which allows +an integer overflow on 32 bit systems. + +A malicious server could send INT_MAX as length, which gets multiplied +by the size of XRectangle. In that case the client won't read the whole +data from server, getting out of sync. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/Region.c | 15 ++++++++++++--- + 1 file changed, 12 insertions(+), 3 deletions(-) + +diff --git a/src/Region.c b/src/Region.c +index cb0cf6e..59bcc1a 100644 +--- a/src/Region.c ++++ b/src/Region.c +@@ -23,6 +23,7 @@ + #ifdef HAVE_CONFIG_H + #include <config.h> + #endif ++#include <limits.h> + #include "Xfixesint.h" + + XserverRegion +@@ -333,9 +334,17 @@ XFixesFetchRegionAndBounds (Display *dpy, + bounds->y = rep.y; + bounds->width = rep.width; + bounds->height = rep.height; +- nbytes = (long) rep.length << 2; +- nrects = rep.length >> 1; +- rects = Xmalloc (nrects * sizeof (XRectangle)); ++ ++ if (rep.length < (INT_MAX >> 2)) { ++ nbytes = (long) rep.length << 2; ++ nrects = rep.length >> 1; ++ rects = Xmalloc (nrects * sizeof (XRectangle)); ++ } else { ++ nbytes = 0; ++ nrects = 0; ++ rects = NULL; ++ } ++ + if (!rects) + { + _XEatDataWords(dpy, rep.length); +-- +2.10.1 + diff --git a/gnu/packages/patches/libxi-CVE-2016-7945-CVE-2016-7946.patch b/gnu/packages/patches/libxi-CVE-2016-7945-CVE-2016-7946.patch new file mode 100644 index 0000000000..ca899e34c0 --- /dev/null +++ b/gnu/packages/patches/libxi-CVE-2016-7945-CVE-2016-7946.patch @@ -0,0 +1,420 @@ +Fix CVE-2016-7945: + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7945 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libXi/commit/?id=19a9cd607de73947fcfb104682f203ffe4e1f4e5 + +From 19a9cd607de73947fcfb104682f203ffe4e1f4e5 Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 22:31:34 +0200 +Subject: [PATCH] Properly validate server responses. + +By validating length fields from server responses, out of boundary +accesses and endless loops can be mitigated. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/XGMotion.c | 3 ++- + src/XGetBMap.c | 3 ++- + src/XGetDCtl.c | 6 ++++-- + src/XGetFCtl.c | 7 ++++++- + src/XGetKMap.c | 14 +++++++++++--- + src/XGetMMap.c | 11 +++++++++-- + src/XIQueryDevice.c | 36 ++++++++++++++++++++++++++++++++++-- + src/XListDev.c | 21 +++++++++++++++------ + src/XOpenDev.c | 13 ++++++++++--- + src/XQueryDv.c | 8 ++++++-- + 10 files changed, 99 insertions(+), 23 deletions(-) + +diff --git a/src/XGMotion.c b/src/XGMotion.c +index 7785843..9433e29 100644 +--- a/src/XGMotion.c ++++ b/src/XGMotion.c +@@ -114,7 +114,8 @@ XGetDeviceMotionEvents( + } + /* rep.axes is a CARD8, so assume max number of axes for bounds check */ + if (rep.nEvents < +- (INT_MAX / (sizeof(XDeviceTimeCoord) + (UCHAR_MAX * sizeof(int))))) { ++ (INT_MAX / (sizeof(XDeviceTimeCoord) + (UCHAR_MAX * sizeof(int)))) && ++ rep.nEvents * (rep.axes + 1) <= rep.length) { + size_t bsize = rep.nEvents * + (sizeof(XDeviceTimeCoord) + (rep.axes * sizeof(int))); + bufp = Xmalloc(bsize); +diff --git a/src/XGetBMap.c b/src/XGetBMap.c +index 002daba..13bb8c6 100644 +--- a/src/XGetBMap.c ++++ b/src/XGetBMap.c +@@ -92,7 +92,8 @@ XGetDeviceButtonMapping( + + status = _XReply(dpy, (xReply *) & rep, 0, xFalse); + if (status == 1) { +- if (rep.length <= (sizeof(mapping) >> 2)) { ++ if (rep.length <= (sizeof(mapping) >> 2) && ++ rep.nElts <= (rep.length << 2)) { + unsigned long nbytes = rep.length << 2; + _XRead(dpy, (char *)mapping, nbytes); + +diff --git a/src/XGetDCtl.c b/src/XGetDCtl.c +index c5d3b53..7f6b396 100644 +--- a/src/XGetDCtl.c ++++ b/src/XGetDCtl.c +@@ -93,7 +93,8 @@ XGetDeviceControl( + if (rep.length > 0) { + unsigned long nbytes; + size_t size = 0; +- if (rep.length < (INT_MAX >> 2)) { ++ if (rep.length < (INT_MAX >> 2) && ++ (rep.length << 2) >= sizeof(xDeviceState)) { + nbytes = (unsigned long) rep.length << 2; + d = Xmalloc(nbytes); + } +@@ -117,7 +118,8 @@ XGetDeviceControl( + size_t val_size; + + r = (xDeviceResolutionState *) d; +- if (r->num_valuators >= (INT_MAX / (3 * sizeof(int)))) ++ if (sizeof(xDeviceResolutionState) > nbytes || ++ r->num_valuators >= (INT_MAX / (3 * sizeof(int)))) + goto out; + val_size = 3 * sizeof(int) * r->num_valuators; + if ((sizeof(xDeviceResolutionState) + val_size) > nbytes) +diff --git a/src/XGetFCtl.c b/src/XGetFCtl.c +index 7fd6d0e..82dcc64 100644 +--- a/src/XGetFCtl.c ++++ b/src/XGetFCtl.c +@@ -73,6 +73,7 @@ XGetFeedbackControl( + XFeedbackState *Sav = NULL; + xFeedbackState *f = NULL; + xFeedbackState *sav = NULL; ++ char *end = NULL; + xGetFeedbackControlReq *req; + xGetFeedbackControlReply rep; + XExtDisplayInfo *info = XInput_find_display(dpy); +@@ -105,10 +106,12 @@ XGetFeedbackControl( + goto out; + } + sav = f; ++ end = (char *)f + nbytes; + _XRead(dpy, (char *)f, nbytes); + + for (i = 0; i < *num_feedbacks; i++) { +- if (f->length > nbytes) ++ if ((char *)f + sizeof(*f) > end || ++ f->length == 0 || f->length > nbytes) + goto out; + nbytes -= f->length; + +@@ -125,6 +128,8 @@ XGetFeedbackControl( + case StringFeedbackClass: + { + xStringFeedbackState *strf = (xStringFeedbackState *) f; ++ if ((char *)f + sizeof(*strf) > end) ++ goto out; + size += sizeof(XStringFeedbackState) + + (strf->num_syms_supported * sizeof(KeySym)); + } +diff --git a/src/XGetKMap.c b/src/XGetKMap.c +index 0540ce4..008a72b 100644 +--- a/src/XGetKMap.c ++++ b/src/XGetKMap.c +@@ -54,6 +54,7 @@ SOFTWARE. + #include <config.h> + #endif + ++#include <limits.h> + #include <X11/extensions/XI.h> + #include <X11/extensions/XIproto.h> + #include <X11/Xlibint.h> +@@ -93,9 +94,16 @@ XGetDeviceKeyMapping(register Display * dpy, XDevice * dev, + return (KeySym *) NULL; + } + if (rep.length > 0) { +- *syms_per_code = rep.keySymsPerKeyCode; +- nbytes = (long)rep.length << 2; +- mapping = (KeySym *) Xmalloc((unsigned)nbytes); ++ if (rep.length < INT_MAX >> 2 && ++ rep.length == rep.keySymsPerKeyCode * keycount) { ++ *syms_per_code = rep.keySymsPerKeyCode; ++ nbytes = (long)rep.length << 2; ++ mapping = (KeySym *) Xmalloc((unsigned)nbytes); ++ } else { ++ *syms_per_code = 0; ++ nbytes = 0; ++ mapping = NULL; ++ } + if (mapping) + _XRead(dpy, (char *)mapping, nbytes); + else +diff --git a/src/XGetMMap.c b/src/XGetMMap.c +index 246698c..33c114f 100644 +--- a/src/XGetMMap.c ++++ b/src/XGetMMap.c +@@ -53,6 +53,7 @@ SOFTWARE. + #include <config.h> + #endif + ++#include <limits.h> + #include <X11/extensions/XI.h> + #include <X11/extensions/XIproto.h> + #include <X11/Xlibint.h> +@@ -85,8 +86,14 @@ XGetDeviceModifierMapping( + SyncHandle(); + return (XModifierKeymap *) NULL; + } +- nbytes = (unsigned long)rep.length << 2; +- res = (XModifierKeymap *) Xmalloc(sizeof(XModifierKeymap)); ++ if (rep.length < (INT_MAX >> 2) && ++ rep.numKeyPerModifier == rep.length >> 1) { ++ nbytes = (unsigned long)rep.length << 2; ++ res = (XModifierKeymap *) Xmalloc(sizeof(XModifierKeymap)); ++ } else { ++ nbytes = 0; ++ res = NULL; ++ } + if (res) { + res->modifiermap = (KeyCode *) Xmalloc(nbytes); + if (res->modifiermap) +diff --git a/src/XIQueryDevice.c b/src/XIQueryDevice.c +index fb8504f..a457cd6 100644 +--- a/src/XIQueryDevice.c ++++ b/src/XIQueryDevice.c +@@ -26,6 +26,7 @@ + #include <config.h> + #endif + ++#include <limits.h> + #include <stdint.h> + #include <X11/Xlibint.h> + #include <X11/extensions/XI2proto.h> +@@ -43,6 +44,7 @@ XIQueryDevice(Display *dpy, int deviceid, int *ndevices_return) + xXIQueryDeviceReq *req; + xXIQueryDeviceReply reply; + char *ptr; ++ char *end; + int i; + char *buf; + +@@ -60,14 +62,24 @@ XIQueryDevice(Display *dpy, int deviceid, int *ndevices_return) + if (!_XReply(dpy, (xReply*) &reply, 0, xFalse)) + goto error; + +- *ndevices_return = reply.num_devices; +- info = Xmalloc((reply.num_devices + 1) * sizeof(XIDeviceInfo)); ++ if (reply.length < INT_MAX / 4) ++ { ++ *ndevices_return = reply.num_devices; ++ info = Xmalloc((reply.num_devices + 1) * sizeof(XIDeviceInfo)); ++ } ++ else ++ { ++ *ndevices_return = 0; ++ info = NULL; ++ } ++ + if (!info) + goto error; + + buf = Xmalloc(reply.length * 4); + _XRead(dpy, buf, reply.length * 4); + ptr = buf; ++ end = buf + reply.length * 4; + + /* info is a null-terminated array */ + info[reply.num_devices].name = NULL; +@@ -79,6 +91,9 @@ XIQueryDevice(Display *dpy, int deviceid, int *ndevices_return) + XIDeviceInfo *lib = &info[i]; + xXIDeviceInfo *wire = (xXIDeviceInfo*)ptr; + ++ if (ptr + sizeof(xXIDeviceInfo) > end) ++ goto error_loop; ++ + lib->deviceid = wire->deviceid; + lib->use = wire->use; + lib->attachment = wire->attachment; +@@ -87,12 +102,23 @@ XIQueryDevice(Display *dpy, int deviceid, int *ndevices_return) + + ptr += sizeof(xXIDeviceInfo); + ++ if (ptr + wire->name_len > end) ++ goto error_loop; ++ + lib->name = Xcalloc(wire->name_len + 1, 1); ++ if (lib->name == NULL) ++ goto error_loop; + strncpy(lib->name, ptr, wire->name_len); ++ lib->name[wire->name_len] = '\0'; + ptr += ((wire->name_len + 3)/4) * 4; + + sz = size_classes((xXIAnyInfo*)ptr, nclasses); + lib->classes = Xmalloc(sz); ++ if (lib->classes == NULL) ++ { ++ Xfree(lib->name); ++ goto error_loop; ++ } + ptr += copy_classes(lib, (xXIAnyInfo*)ptr, &nclasses); + /* We skip over unused classes */ + lib->num_classes = nclasses; +@@ -103,6 +129,12 @@ XIQueryDevice(Display *dpy, int deviceid, int *ndevices_return) + SyncHandle(); + return info; + ++error_loop: ++ while (--i >= 0) ++ { ++ Xfree(info[i].name); ++ Xfree(info[i].classes); ++ } + error: + UnlockDisplay(dpy); + error_unlocked: +diff --git a/src/XListDev.c b/src/XListDev.c +index b85ff3c..f850cd0 100644 +--- a/src/XListDev.c ++++ b/src/XListDev.c +@@ -74,7 +74,7 @@ static int pad_to_xid(int base_size) + } + + static size_t +-SizeClassInfo(xAnyClassPtr *any, int num_classes) ++SizeClassInfo(xAnyClassPtr *any, size_t len, int num_classes) + { + int size = 0; + int j; +@@ -90,6 +90,8 @@ SizeClassInfo(xAnyClassPtr *any, int num_classes) + { + xValuatorInfoPtr v; + ++ if (len < sizeof(v)) ++ return 0; + v = (xValuatorInfoPtr) *any; + size += pad_to_xid(sizeof(XValuatorInfo) + + (v->num_axes * sizeof(XAxisInfo))); +@@ -98,6 +100,8 @@ SizeClassInfo(xAnyClassPtr *any, int num_classes) + default: + break; + } ++ if ((*any)->length > len) ++ return 0; + *any = (xAnyClassPtr) ((char *)(*any) + (*any)->length); + } + +@@ -170,7 +174,7 @@ XListInputDevices( + register Display *dpy, + int *ndevices) + { +- size_t size; ++ size_t s, size; + xListInputDevicesReq *req; + xListInputDevicesReply rep; + xDeviceInfo *list, *slist = NULL; +@@ -178,6 +182,7 @@ XListInputDevices( + XDeviceInfo *clist = NULL; + xAnyClassPtr any, sav_any; + XAnyClassPtr Any; ++ char *end = NULL; + unsigned char *nptr, *Nptr; + int i; + unsigned long rlen; +@@ -213,16 +218,20 @@ XListInputDevices( + + any = (xAnyClassPtr) ((char *)list + (*ndevices * sizeof(xDeviceInfo))); + sav_any = any; ++ end = (char *)list + rlen; + for (i = 0; i < *ndevices; i++, list++) { +- size += SizeClassInfo(&any, (int)list->num_classes); ++ s = SizeClassInfo(&any, end - (char *)any, (int)list->num_classes); ++ if (!s) ++ goto out; ++ size += s; + } + +- Nptr = ((unsigned char *)list) + rlen + 1; ++ Nptr = ((unsigned char *)list) + rlen; + for (i = 0, nptr = (unsigned char *)any; i < *ndevices; i++) { ++ if (nptr >= Nptr) ++ goto out; + size += *nptr + 1; + nptr += (*nptr + 1); +- if (nptr > Nptr) +- goto out; + } + + clist = (XDeviceInfoPtr) Xmalloc(size); +diff --git a/src/XOpenDev.c b/src/XOpenDev.c +index 029dec2..4b3c460 100644 +--- a/src/XOpenDev.c ++++ b/src/XOpenDev.c +@@ -53,6 +53,7 @@ SOFTWARE. + #include <config.h> + #endif + ++#include <limits.h> + #include <X11/extensions/XI.h> + #include <X11/extensions/XIproto.h> + #include <X11/Xlibint.h> +@@ -86,9 +87,15 @@ XOpenDevice( + return (XDevice *) NULL; + } + +- rlen = rep.length << 2; +- dev = (XDevice *) Xmalloc(sizeof(XDevice) + rep.num_classes * +- sizeof(XInputClassInfo)); ++ if (rep.length < INT_MAX >> 2 && ++ (rep.length << 2) >= rep.num_classes * sizeof(xInputClassInfo)) { ++ rlen = rep.length << 2; ++ dev = (XDevice *) Xmalloc(sizeof(XDevice) + rep.num_classes * ++ sizeof(XInputClassInfo)); ++ } else { ++ rlen = 0; ++ dev = NULL; ++ } + if (dev) { + int dlen; /* data length */ + +diff --git a/src/XQueryDv.c b/src/XQueryDv.c +index de1c0e5..7ee2272 100644 +--- a/src/XQueryDv.c ++++ b/src/XQueryDv.c +@@ -73,7 +73,7 @@ XQueryDeviceState( + xQueryDeviceStateReply rep; + XDeviceState *state = NULL; + XInputClass *any, *Any; +- char *data = NULL; ++ char *data = NULL, *end = NULL; + XExtDisplayInfo *info = XInput_find_display(dpy); + + LockDisplay(dpy); +@@ -92,6 +92,7 @@ XQueryDeviceState( + if (rep.length < (INT_MAX >> 2)) { + rlen = (unsigned long) rep.length << 2; + data = Xmalloc(rlen); ++ end = data + rlen; + } + if (!data) { + _XEatDataWords(dpy, rep.length); +@@ -100,7 +101,8 @@ XQueryDeviceState( + _XRead(dpy, data, rlen); + + for (i = 0, any = (XInputClass *) data; i < (int)rep.num_classes; i++) { +- if (any->length > rlen) ++ if ((char *)any + sizeof(XInputClass) > end || ++ any->length == 0 || any->length > rlen) + goto out; + rlen -= any->length; + +@@ -114,6 +116,8 @@ XQueryDeviceState( + case ValuatorClass: + { + xValuatorState *v = (xValuatorState *) any; ++ if ((char *)any + sizeof(xValuatorState) > end) ++ goto out; + size += (sizeof(XValuatorState) + + (v->num_valuators * sizeof(int))); + } +-- +2.10.1 + diff --git a/gnu/packages/patches/libxrandr-CVE-2016-7947-CVE-2016-7948.patch b/gnu/packages/patches/libxrandr-CVE-2016-7947-CVE-2016-7948.patch new file mode 100644 index 0000000000..ece8b18309 --- /dev/null +++ b/gnu/packages/patches/libxrandr-CVE-2016-7947-CVE-2016-7948.patch @@ -0,0 +1,447 @@ +Fix CVE-2016-7947 and CVE-2016-7948. + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7947 +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7948 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libXrandr/commit/?id=a0df3e1c7728205e5c7650b2e6dce684139254a6 + +From a0df3e1c7728205e5c7650b2e6dce684139254a6 Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 22:21:40 +0200 +Subject: [PATCH] Avoid out of boundary accesses on illegal responses + +The responses of the connected X server have to be properly checked +to avoid out of boundary accesses that could otherwise be triggered +by a malicious server. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/XrrConfig.c | 32 +++++++++++++-------- + src/XrrCrtc.c | 83 ++++++++++++++++++++++++++++++++++++++++++------------- + src/XrrMonitor.c | 18 ++++++++++++ + src/XrrOutput.c | 11 ++++++++ + src/XrrProvider.c | 28 ++++++++++++++++--- + src/XrrScreen.c | 52 ++++++++++++++++++++++------------ + 6 files changed, 172 insertions(+), 52 deletions(-) + +diff --git a/src/XrrConfig.c b/src/XrrConfig.c +index 2f0282b..e68c45a 100644 +--- a/src/XrrConfig.c ++++ b/src/XrrConfig.c +@@ -29,6 +29,7 @@ + #include <config.h> + #endif + ++#include <limits.h> + #include <stdio.h> + #include <X11/Xlib.h> + /* we need to be able to manipulate the Display structure on events */ +@@ -272,23 +273,30 @@ static XRRScreenConfiguration *_XRRGetScreenInfo (Display *dpy, + rep.rate = 0; + rep.nrateEnts = 0; + } ++ if (rep.length < INT_MAX >> 2) { ++ nbytes = (long) rep.length << 2; + +- nbytes = (long) rep.length << 2; ++ nbytesRead = (long) (rep.nSizes * SIZEOF (xScreenSizes) + ++ ((rep.nrateEnts + 1)& ~1) * 2 /* SIZEOF(CARD16) */); + +- nbytesRead = (long) (rep.nSizes * SIZEOF (xScreenSizes) + +- ((rep.nrateEnts + 1)& ~1) * 2 /* SIZEOF (CARD16) */); ++ /* ++ * first we must compute how much space to allocate for ++ * randr library's use; we'll allocate the structures in a single ++ * allocation, on cleanlyness grounds. ++ */ + +- /* +- * first we must compute how much space to allocate for +- * randr library's use; we'll allocate the structures in a single +- * allocation, on cleanlyness grounds. +- */ ++ rbytes = sizeof (XRRScreenConfiguration) + ++ (rep.nSizes * sizeof (XRRScreenSize) + ++ rep.nrateEnts * sizeof (int)); + +- rbytes = sizeof (XRRScreenConfiguration) + +- (rep.nSizes * sizeof (XRRScreenSize) + +- rep.nrateEnts * sizeof (int)); ++ scp = (struct _XRRScreenConfiguration *) Xmalloc(rbytes); ++ } else { ++ nbytes = 0; ++ nbytesRead = 0; ++ rbytes = 0; ++ scp = NULL; ++ } + +- scp = (struct _XRRScreenConfiguration *) Xmalloc(rbytes); + if (scp == NULL) { + _XEatData (dpy, (unsigned long) nbytes); + return NULL; +diff --git a/src/XrrCrtc.c b/src/XrrCrtc.c +index 5ae35c5..6665092 100644 +--- a/src/XrrCrtc.c ++++ b/src/XrrCrtc.c +@@ -24,6 +24,7 @@ + #include <config.h> + #endif + ++#include <limits.h> + #include <stdio.h> + #include <X11/Xlib.h> + /* we need to be able to manipulate the Display structure on events */ +@@ -57,22 +58,33 @@ XRRGetCrtcInfo (Display *dpy, XRRScreenResources *resources, RRCrtc crtc) + return NULL; + } + +- nbytes = (long) rep.length << 2; ++ if (rep.length < INT_MAX >> 2) ++ { ++ nbytes = (long) rep.length << 2; + +- nbytesRead = (long) (rep.nOutput * 4 + +- rep.nPossibleOutput * 4); ++ nbytesRead = (long) (rep.nOutput * 4 + ++ rep.nPossibleOutput * 4); + +- /* +- * first we must compute how much space to allocate for +- * randr library's use; we'll allocate the structures in a single +- * allocation, on cleanlyness grounds. +- */ ++ /* ++ * first we must compute how much space to allocate for ++ * randr library's use; we'll allocate the structures in a single ++ * allocation, on cleanlyness grounds. ++ */ + +- rbytes = (sizeof (XRRCrtcInfo) + +- rep.nOutput * sizeof (RROutput) + +- rep.nPossibleOutput * sizeof (RROutput)); ++ rbytes = (sizeof (XRRCrtcInfo) + ++ rep.nOutput * sizeof (RROutput) + ++ rep.nPossibleOutput * sizeof (RROutput)); ++ ++ xci = (XRRCrtcInfo *) Xmalloc(rbytes); ++ } ++ else ++ { ++ nbytes = 0; ++ nbytesRead = 0; ++ rbytes = 0; ++ xci = NULL; ++ } + +- xci = (XRRCrtcInfo *) Xmalloc(rbytes); + if (xci == NULL) { + _XEatDataWords (dpy, rep.length); + UnlockDisplay (dpy); +@@ -194,12 +206,21 @@ XRRGetCrtcGamma (Display *dpy, RRCrtc crtc) + if (!_XReply (dpy, (xReply *) &rep, 0, xFalse)) + goto out; + +- nbytes = (long) rep.length << 2; ++ if (rep.length < INT_MAX >> 2) ++ { ++ nbytes = (long) rep.length << 2; + +- /* three channels of CARD16 data */ +- nbytesRead = (rep.size * 2 * 3); ++ /* three channels of CARD16 data */ ++ nbytesRead = (rep.size * 2 * 3); + +- crtc_gamma = XRRAllocGamma (rep.size); ++ crtc_gamma = XRRAllocGamma (rep.size); ++ } ++ else ++ { ++ nbytes = 0; ++ nbytesRead = 0; ++ crtc_gamma = NULL; ++ } + + if (!crtc_gamma) + { +@@ -357,7 +378,7 @@ XRRGetCrtcTransform (Display *dpy, + xRRGetCrtcTransformReq *req; + int major_version, minor_version; + XRRCrtcTransformAttributes *attr; +- char *extra = NULL, *e; ++ char *extra = NULL, *end = NULL, *e; + int p; + + *attributes = NULL; +@@ -395,9 +416,17 @@ XRRGetCrtcTransform (Display *dpy, + else + { + int extraBytes = rep.length * 4 - CrtcTransformExtra; +- extra = Xmalloc (extraBytes); ++ if (rep.length < INT_MAX / 4 && ++ rep.length * 4 >= CrtcTransformExtra) { ++ extra = Xmalloc (extraBytes); ++ end = extra + extraBytes; ++ } else ++ extra = NULL; + if (!extra) { +- _XEatDataWords (dpy, rep.length - (CrtcTransformExtra >> 2)); ++ if (rep.length > (CrtcTransformExtra >> 2)) ++ _XEatDataWords (dpy, rep.length - (CrtcTransformExtra >> 2)); ++ else ++ _XEatDataWords (dpy, rep.length); + UnlockDisplay (dpy); + SyncHandle (); + return False; +@@ -429,22 +458,38 @@ XRRGetCrtcTransform (Display *dpy, + + e = extra; + ++ if (e + rep.pendingNbytesFilter > end) { ++ XFree (extra); ++ return False; ++ } + memcpy (attr->pendingFilter, e, rep.pendingNbytesFilter); + attr->pendingFilter[rep.pendingNbytesFilter] = '\0'; + e += (rep.pendingNbytesFilter + 3) & ~3; + for (p = 0; p < rep.pendingNparamsFilter; p++) { + INT32 f; ++ if (e + 4 > end) { ++ XFree (extra); ++ return False; ++ } + memcpy (&f, e, 4); + e += 4; + attr->pendingParams[p] = (XFixed) f; + } + attr->pendingNparams = rep.pendingNparamsFilter; + ++ if (e + rep.currentNbytesFilter > end) { ++ XFree (extra); ++ return False; ++ } + memcpy (attr->currentFilter, e, rep.currentNbytesFilter); + attr->currentFilter[rep.currentNbytesFilter] = '\0'; + e += (rep.currentNbytesFilter + 3) & ~3; + for (p = 0; p < rep.currentNparamsFilter; p++) { + INT32 f; ++ if (e + 4 > end) { ++ XFree (extra); ++ return False; ++ } + memcpy (&f, e, 4); + e += 4; + attr->currentParams[p] = (XFixed) f; +diff --git a/src/XrrMonitor.c b/src/XrrMonitor.c +index a9eaa7b..adc5330 100644 +--- a/src/XrrMonitor.c ++++ b/src/XrrMonitor.c +@@ -24,6 +24,7 @@ + #include <config.h> + #endif + ++#include <limits.h> + #include <stdio.h> + #include <X11/Xlib.h> + /* we need to be able to manipulate the Display structure on events */ +@@ -65,6 +66,15 @@ XRRGetMonitors(Display *dpy, Window window, Bool get_active, int *nmonitors) + return NULL; + } + ++ if (rep.length > INT_MAX >> 2 || ++ rep.nmonitors > INT_MAX / SIZEOF(xRRMonitorInfo) || ++ rep.noutputs > INT_MAX / 4 || ++ rep.nmonitors * SIZEOF(xRRMonitorInfo) > INT_MAX - rep.noutputs * 4) { ++ _XEatData (dpy, rep.length); ++ UnlockDisplay (dpy); ++ SyncHandle (); ++ return NULL; ++ } + nbytes = (long) rep.length << 2; + nmon = rep.nmonitors; + noutput = rep.noutputs; +@@ -111,6 +121,14 @@ XRRGetMonitors(Display *dpy, Window window, Bool get_active, int *nmonitors) + mon[m].outputs = output; + buf += SIZEOF (xRRMonitorInfo); + xoutput = (CARD32 *) buf; ++ if (xmon->noutput > rep.noutputs) { ++ Xfree(buf); ++ Xfree(mon); ++ UnlockDisplay (dpy); ++ SyncHandle (); ++ return NULL; ++ } ++ rep.noutputs -= xmon->noutput; + for (o = 0; o < xmon->noutput; o++) + output[o] = xoutput[o]; + output += xmon->noutput; +diff --git a/src/XrrOutput.c b/src/XrrOutput.c +index 85f0b6e..30f3d40 100644 +--- a/src/XrrOutput.c ++++ b/src/XrrOutput.c +@@ -25,6 +25,7 @@ + #include <config.h> + #endif + ++#include <limits.h> + #include <stdio.h> + #include <X11/Xlib.h> + /* we need to be able to manipulate the Display structure on events */ +@@ -60,6 +61,16 @@ XRRGetOutputInfo (Display *dpy, XRRScreenResources *resources, RROutput output) + return NULL; + } + ++ if (rep.length > INT_MAX >> 2 || rep.length < (OutputInfoExtra >> 2)) ++ { ++ if (rep.length > (OutputInfoExtra >> 2)) ++ _XEatDataWords (dpy, rep.length - (OutputInfoExtra >> 2)); ++ else ++ _XEatDataWords (dpy, rep.length); ++ UnlockDisplay (dpy); ++ SyncHandle (); ++ return NULL; ++ } + nbytes = ((long) (rep.length) << 2) - OutputInfoExtra; + + nbytesRead = (long) (rep.nCrtcs * 4 + +diff --git a/src/XrrProvider.c b/src/XrrProvider.c +index 9e620c7..d796cd0 100644 +--- a/src/XrrProvider.c ++++ b/src/XrrProvider.c +@@ -25,6 +25,7 @@ + #include <config.h> + #endif + ++#include <limits.h> + #include <stdio.h> + #include <X11/Xlib.h> + /* we need to be able to manipulate the Display structure on events */ +@@ -59,12 +60,20 @@ XRRGetProviderResources(Display *dpy, Window window) + return NULL; + } + +- nbytes = (long) rep.length << 2; ++ if (rep.length < INT_MAX >> 2) { ++ nbytes = (long) rep.length << 2; + +- nbytesRead = (long) (rep.nProviders * 4); ++ nbytesRead = (long) (rep.nProviders * 4); + +- rbytes = (sizeof(XRRProviderResources) + rep.nProviders * sizeof(RRProvider)); +- xrpr = (XRRProviderResources *) Xmalloc(rbytes); ++ rbytes = (sizeof(XRRProviderResources) + rep.nProviders * ++ sizeof(RRProvider)); ++ xrpr = (XRRProviderResources *) Xmalloc(rbytes); ++ } else { ++ nbytes = 0; ++ nbytesRead = 0; ++ rbytes = 0; ++ xrpr = NULL; ++ } + + if (xrpr == NULL) { + _XEatDataWords (dpy, rep.length); +@@ -121,6 +130,17 @@ XRRGetProviderInfo(Display *dpy, XRRScreenResources *resources, RRProvider provi + return NULL; + } + ++ if (rep.length > INT_MAX >> 2 || rep.length < ProviderInfoExtra >> 2) ++ { ++ if (rep.length < ProviderInfoExtra >> 2) ++ _XEatDataWords (dpy, rep.length); ++ else ++ _XEatDataWords (dpy, rep.length - (ProviderInfoExtra >> 2)); ++ UnlockDisplay (dpy); ++ SyncHandle (); ++ return NULL; ++ } ++ + nbytes = ((long) rep.length << 2) - ProviderInfoExtra; + + nbytesRead = (long)(rep.nCrtcs * 4 + +diff --git a/src/XrrScreen.c b/src/XrrScreen.c +index b8ce7e5..1f7ffe6 100644 +--- a/src/XrrScreen.c ++++ b/src/XrrScreen.c +@@ -24,6 +24,7 @@ + #include <config.h> + #endif + ++#include <limits.h> + #include <stdio.h> + #include <X11/Xlib.h> + /* we need to be able to manipulate the Display structure on events */ +@@ -105,27 +106,36 @@ doGetScreenResources (Display *dpy, Window window, int poll) + xrri->has_rates = _XRRHasRates (xrri->minor_version, xrri->major_version); + } + +- nbytes = (long) rep.length << 2; ++ if (rep.length < INT_MAX >> 2) { ++ nbytes = (long) rep.length << 2; + +- nbytesRead = (long) (rep.nCrtcs * 4 + +- rep.nOutputs * 4 + +- rep.nModes * SIZEOF (xRRModeInfo) + +- ((rep.nbytesNames + 3) & ~3)); ++ nbytesRead = (long) (rep.nCrtcs * 4 + ++ rep.nOutputs * 4 + ++ rep.nModes * SIZEOF (xRRModeInfo) + ++ ((rep.nbytesNames + 3) & ~3)); + +- /* +- * first we must compute how much space to allocate for +- * randr library's use; we'll allocate the structures in a single +- * allocation, on cleanlyness grounds. +- */ ++ /* ++ * first we must compute how much space to allocate for ++ * randr library's use; we'll allocate the structures in a single ++ * allocation, on cleanlyness grounds. ++ */ ++ ++ rbytes = (sizeof (XRRScreenResources) + ++ rep.nCrtcs * sizeof (RRCrtc) + ++ rep.nOutputs * sizeof (RROutput) + ++ rep.nModes * sizeof (XRRModeInfo) + ++ rep.nbytesNames + rep.nModes); /* '\0' terminate names */ + +- rbytes = (sizeof (XRRScreenResources) + +- rep.nCrtcs * sizeof (RRCrtc) + +- rep.nOutputs * sizeof (RROutput) + +- rep.nModes * sizeof (XRRModeInfo) + +- rep.nbytesNames + rep.nModes); /* '\0' terminate names */ ++ xrsr = (XRRScreenResources *) Xmalloc(rbytes); ++ wire_names = (char *) Xmalloc (rep.nbytesNames); ++ } else { ++ nbytes = 0; ++ nbytesRead = 0; ++ rbytes = 0; ++ xrsr = NULL; ++ wire_names = NULL; ++ } + +- xrsr = (XRRScreenResources *) Xmalloc(rbytes); +- wire_names = (char *) Xmalloc (rep.nbytesNames); + if (xrsr == NULL || wire_names == NULL) { + Xfree (xrsr); + Xfree (wire_names); +@@ -174,6 +184,14 @@ doGetScreenResources (Display *dpy, Window window, int poll) + wire_name = wire_names; + for (i = 0; i < rep.nModes; i++) { + xrsr->modes[i].name = names; ++ if (xrsr->modes[i].nameLength > rep.nbytesNames) { ++ Xfree (xrsr); ++ Xfree (wire_names); ++ UnlockDisplay (dpy); ++ SyncHandle (); ++ return NULL; ++ } ++ rep.nbytesNames -= xrsr->modes[i].nameLength; + memcpy (names, wire_name, xrsr->modes[i].nameLength); + names[xrsr->modes[i].nameLength] = '\0'; + names += xrsr->modes[i].nameLength + 1; +-- +2.10.1 + diff --git a/gnu/packages/patches/libxrender-CVE-2016-7949.patch b/gnu/packages/patches/libxrender-CVE-2016-7949.patch new file mode 100644 index 0000000000..3a2be4ea8e --- /dev/null +++ b/gnu/packages/patches/libxrender-CVE-2016-7949.patch @@ -0,0 +1,66 @@ +Fix CVE-2016-7949: + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7949 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libXrender/commit/?id=9362c7ddd1af3b168953d0737877bc52d79c94f4 + +From 9362c7ddd1af3b168953d0737877bc52d79c94f4 Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 21:43:09 +0200 +Subject: [PATCH] Validate lengths while parsing server data. + +Individual lengths inside received server data can overflow +the previously reserved memory. + +It is therefore important to validate every single length +field to not overflow the previously agreed sum of all invidual +length fields. + +v2: consume remaining bytes in the reply buffer on error. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb@laas.fr +--- + src/Xrender.c | 18 ++++++++++++++++++ + 1 file changed, 18 insertions(+) + +diff --git a/src/Xrender.c b/src/Xrender.c +index 3102eb2..71cf3e6 100644 +--- a/src/Xrender.c ++++ b/src/Xrender.c +@@ -533,12 +533,30 @@ XRenderQueryFormats (Display *dpy) + screen->fallback = _XRenderFindFormat (xri, xScreen->fallback); + screen->subpixel = SubPixelUnknown; + xDepth = (xPictDepth *) (xScreen + 1); ++ if (screen->ndepths > rep.numDepths) { ++ Xfree (xri); ++ Xfree (xData); ++ _XEatDataWords (dpy, rep.length); ++ UnlockDisplay (dpy); ++ SyncHandle (); ++ return 0; ++ } ++ rep.numDepths -= screen->ndepths; + for (nd = 0; nd < screen->ndepths; nd++) + { + depth->depth = xDepth->depth; + depth->nvisuals = xDepth->nPictVisuals; + depth->visuals = visual; + xVisual = (xPictVisual *) (xDepth + 1); ++ if (depth->nvisuals > rep.numVisuals) { ++ Xfree (xri); ++ Xfree (xData); ++ _XEatDataWords (dpy, rep.length); ++ UnlockDisplay (dpy); ++ SyncHandle (); ++ return 0; ++ } ++ rep.numVisuals -= depth->nvisuals; + for (nv = 0; nv < depth->nvisuals; nv++) + { + visual->visual = _XRenderFindVisual (dpy, xVisual->visual); +-- +2.10.1 + diff --git a/gnu/packages/patches/libxrender-CVE-2016-7950.patch b/gnu/packages/patches/libxrender-CVE-2016-7950.patch new file mode 100644 index 0000000000..1a64b6e724 --- /dev/null +++ b/gnu/packages/patches/libxrender-CVE-2016-7950.patch @@ -0,0 +1,73 @@ +Fix CVE-2016-7950: + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7950 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libXrender/commit/?id=8fad00b0b647ee662ce4737ca15be033b7a21714 + +From 8fad00b0b647ee662ce4737ca15be033b7a21714 Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 21:42:09 +0200 +Subject: [PATCH] Avoid OOB write in XRenderQueryFilters + +The memory for filter names is reserved right after receiving the reply. +After that, filters are iterated and each individual filter name is +stored in that reserved memory. + +The individual name lengths are not checked for validity, which means +that a malicious server can reserve less memory than it will write to +during each iteration. + +v2: consume remaining bytes in reply buffer on error. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/Filter.c | 13 ++++++++++++- + 1 file changed, 12 insertions(+), 1 deletion(-) + +diff --git a/src/Filter.c b/src/Filter.c +index edfa572..8d701eb 100644 +--- a/src/Filter.c ++++ b/src/Filter.c +@@ -38,7 +38,7 @@ XRenderQueryFilters (Display *dpy, Drawable drawable) + char *name; + char len; + int i; +- unsigned long nbytes, nbytesAlias, nbytesName; ++ unsigned long nbytes, nbytesAlias, nbytesName, reply_left; + + if (!RenderHasExtension (info)) + return NULL; +@@ -114,6 +114,7 @@ XRenderQueryFilters (Display *dpy, Drawable drawable) + * Read the filter aliases + */ + _XRead16Pad (dpy, filters->alias, 2 * rep.numAliases); ++ reply_left = 8 + rep.length - 2 * rep.numAliases;; + + /* + * Read the filter names +@@ -122,9 +123,19 @@ XRenderQueryFilters (Display *dpy, Drawable drawable) + { + int l; + _XRead (dpy, &len, 1); ++ reply_left--; + l = len & 0xff; ++ if ((unsigned long)l + 1 > nbytesName) { ++ _XEatDataWords(dpy, reply_left); ++ Xfree(filters); ++ UnlockDisplay (dpy); ++ SyncHandle (); ++ return NULL; ++ } ++ nbytesName -= l + 1; + filters->filter[i] = name; + _XRead (dpy, name, l); ++ reply_left -= l; + name[l] = '\0'; + name += l + 1; + } +-- +2.10.1 + diff --git a/gnu/packages/patches/libxtst-CVE-2016-7951-CVE-2016-7952.patch b/gnu/packages/patches/libxtst-CVE-2016-7951-CVE-2016-7952.patch new file mode 100644 index 0000000000..9df6cf3f4d --- /dev/null +++ b/gnu/packages/patches/libxtst-CVE-2016-7951-CVE-2016-7952.patch @@ -0,0 +1,152 @@ +Fix CVE-2016-7951 and CVE-2016-7952 + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7951 +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7952 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libXtst/commit/?id=9556ad67af3129ec4a7a4f4b54a0d59701beeae3 + +From 9556ad67af3129ec4a7a4f4b54a0d59701beeae3 Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 21:37:01 +0200 +Subject: [PATCH] Out of boundary access and endless loop in libXtst + +A lack of range checks in libXtst allows out of boundary accesses. +The checks have to be done in-place here, because it cannot be done +without in-depth knowledge of the read data. + +If XRecordStartOfData, XRecordEndOfData, or XRecordClientDied +without a client sequence have attached data, an endless loop would +occur. The do-while-loop continues until the current index reaches +the end. But in these cases, the current index would not be +incremented, leading to an endless processing. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/XRecord.c | 43 +++++++++++++++++++++++++++++++++++++++---- + 1 file changed, 39 insertions(+), 4 deletions(-) + +diff --git a/src/XRecord.c b/src/XRecord.c +index 50420c0..fefd842 100644 +--- a/src/XRecord.c ++++ b/src/XRecord.c +@@ -749,15 +749,23 @@ parse_reply_call_callback( + switch (rep->category) { + case XRecordFromServer: + if (rep->elementHeader&XRecordFromServerTime) { ++ if (current_index + 4 > rep->length << 2) ++ return Error; + EXTRACT_CARD32(rep->clientSwapped, + reply->buf+current_index, + data->server_time); + current_index += 4; + } ++ if (current_index + 1 > rep->length << 2) ++ return Error; + switch (reply->buf[current_index]) { + case X_Reply: /* reply */ ++ if (current_index + 8 > rep->length << 2) ++ return Error; + EXTRACT_CARD32(rep->clientSwapped, + reply->buf+current_index+4, datum_bytes); ++ if (datum_bytes < 0 || datum_bytes > ((INT_MAX >> 2) - 8)) ++ return Error; + datum_bytes = (datum_bytes+8) << 2; + break; + default: /* error or event */ +@@ -766,52 +774,73 @@ parse_reply_call_callback( + break; + case XRecordFromClient: + if (rep->elementHeader&XRecordFromClientTime) { ++ if (current_index + 4 > rep->length << 2) ++ return Error; + EXTRACT_CARD32(rep->clientSwapped, + reply->buf+current_index, + data->server_time); + current_index += 4; + } + if (rep->elementHeader&XRecordFromClientSequence) { ++ if (current_index + 4 > rep->length << 2) ++ return Error; + EXTRACT_CARD32(rep->clientSwapped, + reply->buf+current_index, + data->client_seq); + current_index += 4; + } ++ if (current_index + 4 > rep->length<<2) ++ return Error; + if (reply->buf[current_index+2] == 0 + && reply->buf[current_index+3] == 0) /* needn't swap 0 */ + { /* BIG-REQUESTS */ ++ if (current_index + 8 > rep->length << 2) ++ return Error; + EXTRACT_CARD32(rep->clientSwapped, + reply->buf+current_index+4, datum_bytes); + } else { + EXTRACT_CARD16(rep->clientSwapped, + reply->buf+current_index+2, datum_bytes); + } ++ if (datum_bytes < 0 || datum_bytes > INT_MAX >> 2) ++ return Error; + datum_bytes <<= 2; + break; + case XRecordClientStarted: ++ if (current_index + 8 > rep->length << 2) ++ return Error; + EXTRACT_CARD16(rep->clientSwapped, + reply->buf+current_index+6, datum_bytes); + datum_bytes = (datum_bytes+2) << 2; + break; + case XRecordClientDied: + if (rep->elementHeader&XRecordFromClientSequence) { ++ if (current_index + 4 > rep->length << 2) ++ return Error; + EXTRACT_CARD32(rep->clientSwapped, + reply->buf+current_index, + data->client_seq); + current_index += 4; +- } +- /* fall through */ ++ } else if (current_index < rep->length << 2) ++ return Error; ++ datum_bytes = 0; ++ break; + case XRecordStartOfData: + case XRecordEndOfData: ++ if (current_index < rep->length << 2) ++ return Error; + datum_bytes = 0; ++ break; + } + + if (datum_bytes > 0) { +- if (current_index + datum_bytes > rep->length << 2) ++ if (INT_MAX - datum_bytes < (rep->length << 2) - current_index) { + fprintf(stderr, + "XRecord: %lu-byte reply claims %d-byte element (seq %lu)\n", +- (long)rep->length << 2, current_index + datum_bytes, ++ (unsigned long)rep->length << 2, current_index + datum_bytes, + dpy->last_request_read); ++ return Error; ++ } + /* + * This assignment (and indeed the whole buffer sharing + * scheme) assumes arbitrary 4-byte boundaries are +@@ -863,6 +892,12 @@ XRecordEnableContext(Display *dpy, XRecordContext context, + return 0; + } + ++ if (rep.length > INT_MAX >> 2) { ++ UnlockDisplay(dpy); ++ SyncHandle(); ++ return 0; ++ } ++ + if (rep.length > 0) { + reply = alloc_reply_buffer(info, rep.length<<2); + if (!reply) { +-- +2.10.1 + diff --git a/gnu/packages/patches/libxv-CVE-2016-5407.patch b/gnu/packages/patches/libxv-CVE-2016-5407.patch new file mode 100644 index 0000000000..e6a76c9f70 --- /dev/null +++ b/gnu/packages/patches/libxv-CVE-2016-5407.patch @@ -0,0 +1,162 @@ +Fix CVE-2016-5407: + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-5407 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libXv/commit/?id=d9da580b46a28ab497de2e94fdc7b9ff953dab17 + +From d9da580b46a28ab497de2e94fdc7b9ff953dab17 Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 21:30:03 +0200 +Subject: [PATCH] Protocol handling issues in libXv - CVE-2016-5407 + +The Xv query functions for adaptors and encodings suffer from out of +boundary accesses if a hostile X server sends a maliciously crafted +response. + +A previous fix already checks the received length against fixed values +but ignores additional length specifications which are stored inside +the received data. + +These lengths are accessed in a for-loop. The easiest way to guarantee +a correct processing is by validating all lengths against the +remaining size left before accessing referenced memory. + +This makes the previously applied check obsolete, therefore I removed +it. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/Xv.c | 46 +++++++++++++++++++++++++++++----------------- + 1 file changed, 29 insertions(+), 17 deletions(-) + +diff --git a/src/Xv.c b/src/Xv.c +index e47093a..be450c4 100644 +--- a/src/Xv.c ++++ b/src/Xv.c +@@ -158,6 +158,7 @@ XvQueryAdaptors( + size_t size; + unsigned int ii, jj; + char *name; ++ char *end; + XvAdaptorInfo *pas = NULL, *pa; + XvFormat *pfs, *pf; + char *buffer = NULL; +@@ -197,17 +198,13 @@ XvQueryAdaptors( + /* GET INPUT ADAPTORS */ + + if (rep.num_adaptors == 0) { +- /* If there's no adaptors, there's nothing more to do. */ ++ /* If there are no adaptors, there's nothing more to do. */ + status = Success; + goto out; + } + +- if (size < (rep.num_adaptors * sz_xvAdaptorInfo)) { +- /* If there's not enough data for the number of adaptors, +- then we have a problem. */ +- status = XvBadReply; +- goto out; +- } ++ u.buffer = buffer; ++ end = buffer + size; + + size = rep.num_adaptors * sizeof(XvAdaptorInfo); + if ((pas = Xmalloc(size)) == NULL) { +@@ -225,9 +222,12 @@ XvQueryAdaptors( + pa++; + } + +- u.buffer = buffer; + pa = pas; + for (ii = 0; ii < rep.num_adaptors; ii++) { ++ if (u.buffer + sz_xvAdaptorInfo > end) { ++ status = XvBadReply; ++ goto out; ++ } + pa->type = u.pa->type; + pa->base_id = u.pa->base_id; + pa->num_ports = u.pa->num_ports; +@@ -239,6 +239,10 @@ XvQueryAdaptors( + size = u.pa->name_size; + u.buffer += pad_to_int32(sz_xvAdaptorInfo); + ++ if (u.buffer + size > end) { ++ status = XvBadReply; ++ goto out; ++ } + if ((name = Xmalloc(size + 1)) == NULL) { + status = XvBadAlloc; + goto out; +@@ -259,6 +263,11 @@ XvQueryAdaptors( + + pf = pfs; + for (jj = 0; jj < pa->num_formats; jj++) { ++ if (u.buffer + sz_xvFormat > end) { ++ Xfree(pfs); ++ status = XvBadReply; ++ goto out; ++ } + pf->depth = u.pf->depth; + pf->visual_id = u.pf->visual; + pf++; +@@ -327,6 +336,7 @@ XvQueryEncodings( + size_t size; + unsigned int jj; + char *name; ++ char *end; + XvEncodingInfo *pes = NULL, *pe; + char *buffer = NULL; + union { +@@ -364,17 +374,13 @@ XvQueryEncodings( + /* GET ENCODINGS */ + + if (rep.num_encodings == 0) { +- /* If there's no encodings, there's nothing more to do. */ ++ /* If there are no encodings, there's nothing more to do. */ + status = Success; + goto out; + } + +- if (size < (rep.num_encodings * sz_xvEncodingInfo)) { +- /* If there's not enough data for the number of adaptors, +- then we have a problem. */ +- status = XvBadReply; +- goto out; +- } ++ u.buffer = buffer; ++ end = buffer + size; + + size = rep.num_encodings * sizeof(XvEncodingInfo); + if ((pes = Xmalloc(size)) == NULL) { +@@ -391,10 +397,12 @@ XvQueryEncodings( + pe++; + } + +- u.buffer = buffer; +- + pe = pes; + for (jj = 0; jj < rep.num_encodings; jj++) { ++ if (u.buffer + sz_xvEncodingInfo > end) { ++ status = XvBadReply; ++ goto out; ++ } + pe->encoding_id = u.pe->encoding; + pe->width = u.pe->width; + pe->height = u.pe->height; +@@ -405,6 +413,10 @@ XvQueryEncodings( + size = u.pe->name_size; + u.buffer += pad_to_int32(sz_xvEncodingInfo); + ++ if (u.buffer + size > end) { ++ status = XvBadReply; ++ goto out; ++ } + if ((name = Xmalloc(size + 1)) == NULL) { + status = XvBadAlloc; + goto out; +-- +2.10.1 + diff --git a/gnu/packages/patches/libxvmc-CVE-2016-7953.patch b/gnu/packages/patches/libxvmc-CVE-2016-7953.patch new file mode 100644 index 0000000000..737abdeb9f --- /dev/null +++ b/gnu/packages/patches/libxvmc-CVE-2016-7953.patch @@ -0,0 +1,42 @@ +Fix CVE-2016-7953: + +https://cve.mitre.org/cgi-bin/cvename.cgi?name=CVE-2016-7953 + +Patch copied from upstream source repository: + +https://cgit.freedesktop.org/xorg/lib/libXvMC/commit/?id=2cd95e7da8367cccdcdd5c9b160012d1dec5cbdb + +From 2cd95e7da8367cccdcdd5c9b160012d1dec5cbdb Mon Sep 17 00:00:00 2001 +From: Tobias Stoeckmann <tobias@stoeckmann.org> +Date: Sun, 25 Sep 2016 22:34:27 +0200 +Subject: [PATCH] Avoid buffer underflow on empty strings. + +If an empty string is received from an x-server, do not underrun the +buffer by accessing "rep.nameLen - 1" unconditionally, which could end +up being -1. + +Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org> +Reviewed-by: Matthieu Herrb <matthieu@herrb.eu> +--- + src/XvMC.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/src/XvMC.c b/src/XvMC.c +index 7336760..3ee4212 100644 +--- a/src/XvMC.c ++++ b/src/XvMC.c +@@ -576,9 +576,9 @@ Status XvMCGetDRInfo(Display *dpy, XvPortID port, + if (*name && *busID && tmpBuf) { + _XRead(dpy, tmpBuf, realSize); + strncpy(*name,tmpBuf,rep.nameLen); +- (*name)[rep.nameLen - 1] = '\0'; ++ (*name)[rep.nameLen == 0 ? 0 : rep.nameLen - 1] = '\0'; + strncpy(*busID,tmpBuf+rep.nameLen,rep.busIDLen); +- (*busID)[rep.busIDLen - 1] = '\0'; ++ (*busID)[rep.busIDLen == 0 ? 0 : rep.busIDLen - 1] = '\0'; + XFree(tmpBuf); + } else { + XFree(*name); +-- +2.10.1 + diff --git a/gnu/packages/patches/metabat-remove-compilation-date.patch b/gnu/packages/patches/metabat-remove-compilation-date.patch new file mode 100644 index 0000000000..7672205b22 --- /dev/null +++ b/gnu/packages/patches/metabat-remove-compilation-date.patch @@ -0,0 +1,16 @@ +Remove the reference to the compilation date so that the build is +reproducible. + +diff --git a/src/metabat.cpp b/src/metabat.cpp +index 88e06de..c95cb1a 100644 +--- a/src/metabat.cpp ++++ b/src/metabat.cpp +@@ -49,7 +49,7 @@ int main(int ac, char* av[]) { + po::notify(vm); + + if (vm.count("help") || inFile.length() == 0 || outFile.length() == 0) { +- cerr << "\nMetaBAT: Metagenome Binning based on Abundance and Tetranucleotide frequency (version " << version << "; " << __DATE__ << " " << __TIME__ << ")" << endl; ++ cerr << "\nMetaBAT: Metagenome Binning based on Abundance and Tetranucleotide frequency (version " << version << "; unknown compilation date)" << endl; + cerr << "by Don Kang (ddkang@lbl.gov), Jeff Froula, Rob Egan, and Zhong Wang (zhongwang@lbl.gov) \n" << endl; + cerr << desc << endl << endl; + diff --git a/gnu/packages/patches/rush-CVE-2013-6889.patch b/gnu/packages/patches/rush-CVE-2013-6889.patch deleted file mode 100644 index 862528a12c..0000000000 --- a/gnu/packages/patches/rush-CVE-2013-6889.patch +++ /dev/null @@ -1,23 +0,0 @@ -commit 00bdccd429517f12dbf37ab4397ddec3e51a2738 -Author: Mats Erik Andersson <gnu@gisladisker.se> -Date: Mon Jan 20 13:33:52 2014 +0200 - - Protect against CVE-2013-6889 (tiny change). - - Reset the effective user identification in testing mode. - -diff --git a/src/rush.c b/src/rush.c -index 45d737a..dc6518e 100644 ---- a/src/rush.c -+++ b/src/rush.c -@@ -980,6 +980,10 @@ main(int argc, char **argv) - } else if (argc > optind) - die(usage_error, NULL, _("invalid command line")); - -+ /* Relinquish root privileges in test mode */ -+ if (lint_option) -+ setuid(getuid()); -+ - if (test_user_name) { - struct passwd *pw = getpwnam(test_user_name); - if (!pw) |