Fix buffer overflows in TIFF, PNG, IRIS, DPX, HDR and AVI loading.

Solves these security issues from T52924:
CVE-2017-2899
CVE-2017-2900
CVE-2017-2901
CVE-2017-2902
CVE-2017-2903
CVE-2017-2904
CVE-2017-2905
CVE-2017-2906
CVE-2017-2907
CVE-2017-2918

Differential Revision: https://developer.blender.org/D2999
This commit is contained in:
2018-01-14 14:19:57 +01:00
parent a6700362c7
commit d30cc1ea0b
20 changed files with 349 additions and 289 deletions

View File

@@ -260,7 +260,6 @@ struct ImBuf *imb_loadiris(const uchar *mem, size_t size, int flags, char colors
const uchar *mem_end = mem + size;
MFileOffset _inf_data = {mem, 0}, *inf = &_inf_data;
IMAGE image;
int x, y, z, tablen;
int bpp, rle, cur, badorder;
ImBuf *ibuf;
uchar dirty_flag = 0;
@@ -304,7 +303,7 @@ struct ImBuf *imb_loadiris(const uchar *mem, size_t size, int flags, char colors
}
if (rle) {
tablen = ysize * zsize * sizeof(int);
size_t tablen = (size_t)ysize * (size_t)zsize * sizeof(int);
MFILE_SEEK(inf, HEADER_SIZE);
uint *starttab = MEM_mallocN(tablen, "iris starttab");
@@ -321,8 +320,8 @@ struct ImBuf *imb_loadiris(const uchar *mem, size_t size, int flags, char colors
/* check data order */
cur = 0;
badorder = 0;
for (y = 0; y < ysize; y++) {
for (z = 0; z < zsize; z++) {
for (size_t y = 0; y < ysize; y++) {
for (size_t z = 0; z < zsize; z++) {
if (starttab[y + z * ysize] < cur) {
badorder = 1;
break;
@@ -336,14 +335,17 @@ struct ImBuf *imb_loadiris(const uchar *mem, size_t size, int flags, char colors
if (bpp == 1) {
ibuf = IMB_allocImBuf(xsize, ysize, 8 * zsize, IB_rect);
if (!ibuf) {
goto fail_rle;
}
if (ibuf->planes > 32) ibuf->planes = 32;
base = ibuf->rect;
zbase = (uint *)ibuf->zbuf;
if (badorder) {
for (z = 0; z < zsize; z++) {
for (size_t z = 0; z < zsize; z++) {
lptr = base;
for (y = 0; y < ysize; y++) {
for (size_t y = 0; y < ysize; y++) {
MFILE_SEEK(inf, starttab[y + z * ysize]);
rledat = MFILE_DATA(inf);
MFILE_STEP(inf, lengthtab[y + z * ysize]);
@@ -358,12 +360,12 @@ struct ImBuf *imb_loadiris(const uchar *mem, size_t size, int flags, char colors
else {
lptr = base;
zptr = zbase;
for (y = 0; y < ysize; y++) {
for (size_t y = 0; y < ysize; y++) {
uint *lptr_next = lptr + xsize;
uint *zptr_next = zptr + xsize;
for (z = 0; z < zsize; z++) {
for (size_t z = 0; z < zsize; z++) {
MFILE_SEEK(inf, starttab[y + z * ysize]);
rledat = MFILE_DATA(inf);
MFILE_STEP(inf, lengthtab[y + z * ysize]);
@@ -386,13 +388,16 @@ struct ImBuf *imb_loadiris(const uchar *mem, size_t size, int flags, char colors
else { /* bpp == 2 */
ibuf = IMB_allocImBuf(xsize, ysize, 32, (flags & IB_rect) | IB_rectfloat);
if (!ibuf) {
goto fail_rle;
}
fbase = ibuf->rect_float;
if (badorder) {
for (z = 0; z < zsize; z++) {
for (size_t z = 0; z < zsize; z++) {
fptr = fbase;
for (y = 0; y < ysize; y++) {
for (size_t y = 0; y < ysize; y++) {
MFILE_SEEK(inf, starttab[y + z * ysize]);
rledat = MFILE_DATA(inf);
MFILE_STEP(inf, lengthtab[y + z * ysize]);
@@ -408,9 +413,9 @@ struct ImBuf *imb_loadiris(const uchar *mem, size_t size, int flags, char colors
fptr = fbase;
float *fptr_next = fptr + (xsize * 4);
for (y = 0; y < ysize; y++) {
for (size_t y = 0; y < ysize; y++) {
for (z = 0; z < zsize; z++) {
for (size_t z = 0; z < zsize; z++) {
MFILE_SEEK(inf, starttab[y + z * ysize]);
rledat = MFILE_DATA(inf);
MFILE_STEP(inf, lengthtab[y + z * ysize]);
@@ -426,6 +431,10 @@ struct ImBuf *imb_loadiris(const uchar *mem, size_t size, int flags, char colors
fail_rle:
MEM_freeN(starttab);
MEM_freeN(lengthtab);
if (!ibuf) {
return NULL;
}
}
else {
@@ -435,6 +444,9 @@ fail_rle:
if (bpp == 1) {
ibuf = IMB_allocImBuf(xsize, ysize, 8 * zsize, IB_rect);
if (!ibuf) {
goto fail_uncompressed;
}
if (ibuf->planes > 32) ibuf->planes = 32;
base = ibuf->rect;
@@ -443,12 +455,12 @@ fail_rle:
MFILE_SEEK(inf, HEADER_SIZE);
rledat = MFILE_DATA(inf);
for (z = 0; z < zsize; z++) {
for (size_t z = 0; z < zsize; z++) {
if (z < 4) lptr = base;
else if (z < 8) lptr = zbase;
for (y = 0; y < ysize; y++) {
for (size_t y = 0; y < ysize; y++) {
const uchar *rledat_next = rledat + xsize;
const int z_ofs = 3 - z;
MFILE_CAPACITY_AT_PTR_OK_OR_FAIL(rledat_next + z_ofs);
@@ -462,17 +474,20 @@ fail_rle:
else { /* bpp == 2 */
ibuf = IMB_allocImBuf(xsize, ysize, 32, (flags & IB_rect) | IB_rectfloat);
if (!ibuf) {
goto fail_uncompressed;
}
fbase = ibuf->rect_float;
MFILE_SEEK(inf, HEADER_SIZE);
rledat = MFILE_DATA(inf);
for (z = 0; z < zsize; z++) {
for (size_t z = 0; z < zsize; z++) {
fptr = fbase;
for (y = 0; y < ysize; y++) {
for (size_t y = 0; y < ysize; y++) {
const uchar *rledat_next = rledat + xsize * 2;
const int z_ofs = 3 - z;
MFILE_CAPACITY_AT_PTR_OK_OR_FAIL(rledat_next + z_ofs);
@@ -485,7 +500,9 @@ fail_rle:
}
#undef MFILE_CAPACITY_AT_PTR_OK_OR_FAIL
fail_uncompressed:
(void)0;
if (!ibuf) {
return NULL;
}
}
if (bpp == 1) {
@@ -493,7 +510,7 @@ fail_uncompressed:
if (image.zsize == 1) {
rect = (uchar *) ibuf->rect;
for (x = ibuf->x * ibuf->y; x > 0; x--) {
for (size_t x = (size_t)ibuf->x * (size_t)ibuf->y; x > 0; x--) {
rect[0] = 255;
rect[1] = rect[2] = rect[3];
rect += 4;
@@ -502,7 +519,7 @@ fail_uncompressed:
else if (image.zsize == 2) {
/* grayscale with alpha */
rect = (uchar *) ibuf->rect;
for (x = ibuf->x * ibuf->y; x > 0; x--) {
for (size_t x = (size_t)ibuf->x * (size_t)ibuf->y; x > 0; x--) {
rect[0] = rect[2];
rect[1] = rect[2] = rect[3];
rect += 4;
@@ -511,7 +528,7 @@ fail_uncompressed:
else if (image.zsize == 3) {
/* add alpha */
rect = (uchar *) ibuf->rect;
for (x = ibuf->x * ibuf->y; x > 0; x--) {
for (size_t x = (size_t)ibuf->x * (size_t)ibuf->y; x > 0; x--) {
rect[0] = 255;
rect += 4;
}
@@ -522,7 +539,7 @@ fail_uncompressed:
if (image.zsize == 1) {
fbase = ibuf->rect_float;
for (x = ibuf->x * ibuf->y; x > 0; x--) {
for (size_t x = (size_t)ibuf->x * (size_t)ibuf->y; x > 0; x--) {
fbase[0] = 1;
fbase[1] = fbase[2] = fbase[3];
fbase += 4;
@@ -531,7 +548,7 @@ fail_uncompressed:
else if (image.zsize == 2) {
/* grayscale with alpha */
fbase = ibuf->rect_float;
for (x = ibuf->x * ibuf->y; x > 0; x--) {
for (size_t x = (size_t)ibuf->x * (size_t)ibuf->y; x > 0; x--) {
fbase[0] = fbase[2];
fbase[1] = fbase[2] = fbase[3];
fbase += 4;
@@ -540,7 +557,7 @@ fail_uncompressed:
else if (image.zsize == 3) {
/* add alpha */
fbase = ibuf->rect_float;
for (x = ibuf->x * ibuf->y; x > 0; x--) {
for (size_t x = (size_t)ibuf->x * (size_t)ibuf->y; x > 0; x--) {
fbase[0] = 1;
fbase += 4;
}