images: more strict check of pcx

checked with https://samples.ffmpeg.org/image-samples/pcx/
This commit is contained in:
Denis Pauk 2024-07-15 04:09:11 +03:00
parent 3ba0f35636
commit 4e61cbccc2

View file

@ -135,7 +135,8 @@ fixQuitScreen(byte* px)
} }
static const byte * static const byte *
PCX_RLE_Decode(byte *pix, byte *pix_max, const byte *raw, const byte *raw_max, int bytes_per_line) PCX_RLE_Decode(byte *pix, byte *pix_max, const byte *raw, const byte *raw_max,
int bytes_per_line, qboolean *image_issues)
{ {
int x; int x;
@ -147,6 +148,7 @@ PCX_RLE_Decode(byte *pix, byte *pix_max, const byte *raw, const byte *raw_max, i
if (raw >= raw_max) if (raw >= raw_max)
{ {
// no place for read // no place for read
*image_issues = true;
return raw; return raw;
} }
dataByte = *raw++; dataByte = *raw++;
@ -157,6 +159,7 @@ PCX_RLE_Decode(byte *pix, byte *pix_max, const byte *raw, const byte *raw_max, i
if (raw >= raw_max) if (raw >= raw_max)
{ {
// no place for read // no place for read
*image_issues = true;
return raw; return raw;
} }
dataByte = *raw++; dataByte = *raw++;
@ -171,6 +174,7 @@ PCX_RLE_Decode(byte *pix, byte *pix_max, const byte *raw, const byte *raw_max, i
if (pix_max <= (pix + x)) if (pix_max <= (pix + x))
{ {
// no place for write // no place for write
*image_issues = true;
return raw; return raw;
} }
else else
@ -217,7 +221,12 @@ PCX_Decode(const char *name, const byte *raw, int len, byte **pic, byte **palett
if ((pcx->manufacturer != 0x0a) || if ((pcx->manufacturer != 0x0a) ||
(pcx->version != 5) || (pcx->version != 5) ||
(pcx->encoding != 1)) (pcx->encoding != 1) ||
(pcx_width <= 0) ||
(pcx_height <= 0) ||
(bytes_per_line <= 0) ||
(pcx->color_planes <= 0) ||
(pcx->bits_per_pixel <= 0))
{ {
Com_Printf("%s: Bad pcx file %s: version: %d:%d, encoding: %d\n", Com_Printf("%s: Bad pcx file %s: version: %d:%d, encoding: %d\n",
__func__, name, pcx->manufacturer, pcx->version, pcx->encoding); __func__, name, pcx->manufacturer, pcx->version, pcx->encoding);
@ -273,7 +282,7 @@ PCX_Decode(const char *name, const byte *raw, int len, byte **pic, byte **palett
{ {
data = PCX_RLE_Decode(line, line + (pcx_width + 1) * pcx->color_planes, data = PCX_RLE_Decode(line, line + (pcx_width + 1) * pcx->color_planes,
data, (byte *)pcx + len, data, (byte *)pcx + len,
bytes_per_line * pcx->color_planes); bytes_per_line * pcx->color_planes, &image_issues);
for (x = 0; x <= pcx_width; x++) { for (x = 0; x <= pcx_width; x++) {
int j; int j;
@ -314,7 +323,7 @@ PCX_Decode(const char *name, const byte *raw, int len, byte **pic, byte **palett
data = PCX_RLE_Decode(line, line + bytes_per_line * pcx->color_planes, data = PCX_RLE_Decode(line, line + bytes_per_line * pcx->color_planes,
data, (byte *)pcx + len, data, (byte *)pcx + len,
bytes_per_line * pcx->color_planes); bytes_per_line * pcx->color_planes, &image_issues);
for (x = 0; x <= pcx_width; x++) for (x = 0; x <= pcx_width; x++)
{ {
@ -332,12 +341,7 @@ PCX_Decode(const char *name, const byte *raw, int len, byte **pic, byte **palett
} }
free(line); free(line);
} }
else if (pcx->color_planes == 1 && else if (pcx->color_planes == 1 && pcx->bits_per_pixel == 8)
(pcx->bits_per_pixel == 2 ||
pcx->bits_per_pixel == 4 ||
pcx->bits_per_pixel == 8))
{
if (pcx->bits_per_pixel == 8)
{ {
int y; int y;
@ -372,10 +376,11 @@ PCX_Decode(const char *name, const byte *raw, int len, byte **pic, byte **palett
{ {
data = PCX_RLE_Decode(pix, pix + pcx_width + 1, data = PCX_RLE_Decode(pix, pix + pcx_width + 1,
data, (byte *)pcx + len, data, (byte *)pcx + len,
bytes_per_line); bytes_per_line, &image_issues);
} }
} }
else else if (pcx->color_planes == 1 &&
(pcx->bits_per_pixel == 2 || pcx->bits_per_pixel == 4))
{ {
int y; int y;
@ -403,7 +408,7 @@ PCX_Decode(const char *name, const byte *raw, int len, byte **pic, byte **palett
data = PCX_RLE_Decode(line, line + bytes_per_line, data = PCX_RLE_Decode(line, line + bytes_per_line,
data, (byte *)pcx + len, data, (byte *)pcx + len,
bytes_per_line); bytes_per_line, &image_issues);
mask = (1 << pcx->bits_per_pixel) - 1; mask = (1 << pcx->bits_per_pixel) - 1;
div = 8 / pcx->bits_per_pixel; div = 8 / pcx->bits_per_pixel;
@ -426,7 +431,6 @@ PCX_Decode(const char *name, const byte *raw, int len, byte **pic, byte **palett
free(line); free(line);
} }
}
else else
{ {
Com_Printf("%s: Bad pcx file %s: planes: %d, bits: %d\n", Com_Printf("%s: Bad pcx file %s: planes: %d, bits: %d\n",