dcraw/dcraw-9.25.0-CVE-2013-1438.patch
2015-05-20 17:16:22 +02:00

102 lines
3.7 KiB
Diff

From 16a638f66b5a6d5c6e83e817db58a92cfe9f62b6 Mon Sep 17 00:00:00 2001
From: Nils Philippsen <nils@redhat.com>
Date: Tue, 19 May 2015 14:58:47 +0200
Subject: [PATCH] CVE-2013-1438: fix various security issues
This fixes division by zero, infinite loop, and null pointer dereference
bugs. Ported from Alex Tutubalin's fix in LibRaw (commit
9ae25d8c3a6bfb40c582538193264f74c9b93bc0).
Don't check 'huff' at the beginning of ljpeg_diff() because it can never
be NULL the way it is called elsewhere in the program.
---
dcraw.c | 30 +++++++++++++++++++++---------
1 file changed, 21 insertions(+), 9 deletions(-)
diff --git a/dcraw.c b/dcraw.c
index cc7f764..22e0bb5 100644
--- a/dcraw.c
+++ b/dcraw.c
@@ -939,6 +939,8 @@ void CLASS lossless_jpeg_load_raw()
ushort *rp;
if (!ljpeg_start (&jh, 0)) return;
+ if (jh.wide < 1 || jh.high < 1 || jh.clrs < 1 || jh.bits < 1)
+ longjmp (failure, 2);
jwide = jh.wide * jh.clrs;
for (jrow=0; jrow < jh.high; jrow++) {
@@ -958,6 +960,8 @@ void CLASS lossless_jpeg_load_raw()
}
if (raw_width == 3984 && (col -= 2) < 0)
col += (row--,raw_width);
+ if (row > raw_height)
+ longjmp (failure, 3);
if ((unsigned) row < raw_height) RAW(row,col) = val;
if (++col >= raw_width)
col = (row++,0);
@@ -5783,6 +5787,7 @@ int CLASS parse_tiff_ifd (int base)
data_offset = get4()+base;
ifd++; break;
}
+ if(len > 1000) len=1000; /* 1000 SubIFDs is enough */
while (len--) {
i = ftell(ifp);
fseek (ifp, get4()+base, SEEK_SET);
@@ -6010,7 +6015,7 @@ guess_cfa_pc:
break;
case 50715: /* BlackLevelDeltaH */
case 50716: /* BlackLevelDeltaV */
- for (num=i=0; i < len; i++)
+ for (num=i=0; i < len && i < 65536; i++)
num += getreal(type);
black += num/len + 0.5;
break;
@@ -6135,9 +6140,13 @@ void CLASS apply_tiff()
if (thumb_offset) {
fseek (ifp, thumb_offset, SEEK_SET);
if (ljpeg_start (&jh, 1)) {
- thumb_misc = jh.bits;
- thumb_width = jh.wide;
- thumb_height = jh.high;
+ if ((unsigned)jh.bits < 17 && (unsigned)jh.wide < 0x10000 &&
+ (unsigned)jh.high < 0x10000)
+ {
+ thumb_misc = jh.bits;
+ thumb_width = jh.wide;
+ thumb_height = jh.high;
+ }
}
}
for (i=0; i < tiff_nifds; i++) {
@@ -6145,8 +6154,9 @@ void CLASS apply_tiff()
max_samp = tiff_ifd[i].samples;
if (max_samp > 3) max_samp = 3;
if ((tiff_ifd[i].comp != 6 || tiff_ifd[i].samples != 3) &&
- (tiff_ifd[i].width | tiff_ifd[i].height) < 0x10000 &&
- tiff_ifd[i].width*tiff_ifd[i].height > raw_width*raw_height) {
+ (tiff_ifd[i].width | tiff_ifd[i].height) < 0x10000 &&
+ (unsigned)tiff_ifd[i].bps < 33 && (unsigned)tiff_ifd[i].samples < 13 &&
+ tiff_ifd[i].width*tiff_ifd[i].height > raw_width*raw_height) {
raw_width = tiff_ifd[i].width;
raw_height = tiff_ifd[i].height;
tiff_bps = tiff_ifd[i].bps;
@@ -6240,9 +6250,11 @@ void CLASS apply_tiff()
is_raw = 0;
for (i=0; i < tiff_nifds; i++)
if (i != raw && tiff_ifd[i].samples == max_samp &&
- tiff_ifd[i].width * tiff_ifd[i].height / (SQR(tiff_ifd[i].bps)+1) >
- thumb_width * thumb_height / (SQR(thumb_misc)+1)
- && tiff_ifd[i].comp != 34892) {
+ tiff_ifd[i].bps > 0 && tiff_ifd[i].bps < 33 &&
+ ((unsigned)(tiff_ifd[i].width | tiff_ifd[i].height)) < 0x10000 &&
+ tiff_ifd[i].width * tiff_ifd[i].height / (SQR(tiff_ifd[i].bps)+1) >
+ thumb_width * thumb_height / (SQR(thumb_misc)+1)
+ && tiff_ifd[i].comp != 34892) {
thumb_width = tiff_ifd[i].width;
thumb_height = tiff_ifd[i].height;
thumb_offset = tiff_ifd[i].offset;
--
2.4.1