summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAlan Coopersmith <alan.coopersmith@oracle.com>2013-03-09 14:40:33 -0800
committerAlan Coopersmith <alan.coopersmith@oracle.com>2013-04-26 17:32:34 -0700
commit67ecdcf7e29de9fa78b421122620525ed2c7db88 (patch)
treeffb91f5de73a7937d33fe243dfdca704bcbce4af
parent96d1da55a08c4cd52b763cb07bdce5cdcbec4da8 (diff)
integer overflow in XeviGetVisualInfo() [CVE-2013-1982 4/6]
If the number of visuals or conflicts reported by the server is large enough that it overflows when multiplied by the size of the appropriate struct, then memory corruption can occur when more bytes are read from the X server than the size of the buffer we allocated to hold them. Reported-by: Ilja Van Sprundel <ivansprundel@ioactive.com> Signed-off-by: Alan Coopersmith <alan.coopersmith@oracle.com>
-rw-r--r--src/XEVI.c25
1 files changed, 18 insertions, 7 deletions
diff --git a/src/XEVI.c b/src/XEVI.c
index 0125c51..5a95583 100644
--- a/src/XEVI.c
+++ b/src/XEVI.c
@@ -30,6 +30,7 @@ THE USE OR PERFORMANCE OF THIS SOFTWARE.
#include <X11/extensions/Xext.h>
#include <X11/extensions/extutil.h>
#include <X11/Xutil.h>
+#include <limits.h>
#include "eat.h"
static XExtensionInfo *xevi_info;/* needs to move to globals.c */
@@ -165,13 +166,20 @@ Status XeviGetVisualInfo(
return BadAccess;
}
Xfree(temp_visual);
- sz_info = rep.n_info * sizeof(ExtendedVisualInfo);
- sz_xInfo = rep.n_info * sz_xExtendedVisualInfo;
- sz_conflict = rep.n_conflicts * sizeof(VisualID);
- sz_xConflict = rep.n_conflicts * sz_VisualID32;
- infoPtr = *evi_return = (ExtendedVisualInfo *)Xmalloc(sz_info + sz_conflict);
- xInfoPtr = temp_xInfo = (xExtendedVisualInfo *)Xmalloc(sz_xInfo);
- xConflictPtr = temp_conflict = (VisualID32 *)Xmalloc(sz_xConflict);
+ if ((rep.n_info < 65536) && (rep.n_conflicts < 65536)) {
+ sz_info = rep.n_info * sizeof(ExtendedVisualInfo);
+ sz_xInfo = rep.n_info * sz_xExtendedVisualInfo;
+ sz_conflict = rep.n_conflicts * sizeof(VisualID);
+ sz_xConflict = rep.n_conflicts * sz_VisualID32;
+ *evi_return = Xmalloc(sz_info + sz_conflict);
+ temp_xInfo = Xmalloc(sz_xInfo);
+ temp_conflict = Xmalloc(sz_xConflict);
+ } else {
+ sz_xInfo = sz_xConflict = 0;
+ *evi_return = NULL;
+ temp_xInfo = NULL;
+ temp_conflict = NULL;
+ }
if (!*evi_return || !temp_xInfo || !temp_conflict) {
_XEatDataWords(dpy, rep.length);
UnlockDisplay(dpy);
@@ -188,6 +196,9 @@ Status XeviGetVisualInfo(
_XRead(dpy, (char *)temp_conflict, sz_xConflict);
UnlockDisplay(dpy);
SyncHandle();
+ infoPtr = *evi_return;
+ xInfoPtr = temp_xInfo;
+ xConflictPtr = temp_conflict;
n_data = rep.n_info;
conflict = (VisualID *)(infoPtr + n_data);
while (n_data-- > 0) {