From 2048abf84e2d998666be84d4f16f8fec7617d4de Mon Sep 17 00:00:00 2001 From: Ozkan Sezer Date: Wed, 10 Jul 2019 23:51:28 +0300 Subject: [PATCH] xpm: backport security and bug fixes from main 2.0 branch: TALOS-2019-0843: XPM image color code code execution vulnerability TALOS-2019-0844: XPM image colorhash parsing Code Execution Vulnerability mainstream commits: https://hg.libsdl.org/SDL_image/rev/95fc7da55247 https://hg.libsdl.org/SDL_image/rev/26061e601c81 --- IMG_xpm.c | 32 ++++++++++++++++++++++++++------ 1 file changed, 26 insertions(+), 6 deletions(-) diff --git a/IMG_xpm.c b/IMG_xpm.c index 59eb1981..cc87d4c0 100644 --- a/IMG_xpm.c +++ b/IMG_xpm.c @@ -106,7 +106,7 @@ static struct color_hash *create_colorhash(int maxnum) /* we know how many entries we need, so we can allocate everything here */ - hash = (struct color_hash *)malloc(sizeof *hash); + hash = (struct color_hash *)calloc(1, sizeof(*hash)); if(!hash) return NULL; @@ -115,15 +115,29 @@ static struct color_hash *create_colorhash(int maxnum) ; hash->size = s; hash->maxnum = maxnum; + bytes = hash->size * sizeof(struct hash_entry **); - hash->entries = NULL; /* in case malloc fails */ - hash->table = (struct hash_entry **)malloc(bytes); + /* Check for overflow */ + if ((bytes / sizeof(struct hash_entry **)) != hash->size) { + IMG_SetError("memory allocation overflow"); + free(hash); + return NULL; + } + hash->table = (struct hash_entry **)calloc(1, bytes); if(!hash->table) { free(hash); return NULL; } - memset(hash->table, 0, bytes); - hash->entries = (struct hash_entry *)malloc(maxnum * sizeof(struct hash_entry)); + + bytes = maxnum * sizeof(struct hash_entry); + /* Check for overflow */ + if ((bytes / sizeof(struct hash_entry)) != maxnum) { + IMG_SetError("memory allocation overflow"); + free(hash->table); + free(hash); + return NULL; + } + hash->entries = (struct hash_entry *)calloc(1, bytes); if(!hash->entries) { free(hash->table); free(hash); @@ -362,6 +376,11 @@ static SDL_Surface *load_xpm(char **xpm, SDL_RWops *src) goto done; } + /* Check for allocation overflow */ + if ((size_t)(ncolors * cpp)/cpp != ncolors) { + error = "Invalid color specification"; + goto done; + } keystrings = (char *)malloc(ncolors * cpp); if(!keystrings) { error = "Out of memory"; @@ -429,8 +448,9 @@ static SDL_Surface *load_xpm(char **xpm, SDL_RWops *src) c->g = (Uint8)(rgb >> 8); c->b = (Uint8)(rgb); pixel = index; - } else + } else { pixel = rgb; + } add_colorhash(colors, nextkey, cpp, pixel); nextkey += cpp; if(rgb == 0xffffffff)