diff options
author | Marti Maria <mmaria@abindustries.com> | 2022-01-14 13:29:58 +0100 |
---|---|---|
committer | Marti Maria <mmaria@abindustries.com> | 2022-01-14 13:29:58 +0100 |
commit | e090fcf461b9cd86733cd642856ab478ee6278e8 (patch) | |
tree | 84ef0b787940e8d388f36c286d86f80c40aba273 | |
parent | 1c3ccf4724333743dbef6d828bb22fc7776ad1e8 (diff) | |
download | lcms2-e090fcf461b9cd86733cd642856ab478ee6278e8.tar.gz |
more code guards on uncommon tags
Not used on normal color management, but it's good to have robust code.
-rw-r--r-- | src/cmstypes.c | 70 |
1 files changed, 52 insertions, 18 deletions
diff --git a/src/cmstypes.c b/src/cmstypes.c index d64369f..b855d2e 100644 --- a/src/cmstypes.c +++ b/src/cmstypes.c @@ -3577,40 +3577,55 @@ void *Type_UcrBg_Read(struct _cms_typehandler_struct* self, cmsIOHANDLER* io, cm SignedSizeOfTag -= sizeof(cmsUInt32Number); n ->Ucr = cmsBuildTabulatedToneCurve16(self ->ContextID, CountUcr, NULL); - if (n ->Ucr == NULL) return NULL; + if (n ->Ucr == NULL) goto error; - if (SignedSizeOfTag < (cmsInt32Number)CountUcr * sizeof(cmsUInt16Number)) return NULL; - if (!_cmsReadUInt16Array(io, CountUcr, n ->Ucr->Table16)) return NULL; + if (SignedSizeOfTag < (cmsInt32Number)CountUcr * sizeof(cmsUInt16Number)) goto error; + if (!_cmsReadUInt16Array(io, CountUcr, n ->Ucr->Table16)) goto error; SignedSizeOfTag -= CountUcr * sizeof(cmsUInt16Number); // Second curve is Black generation - if (SignedSizeOfTag < sizeof(cmsUInt32Number)) return NULL; - if (!_cmsReadUInt32Number(io, &CountBg)) return NULL; + if (SignedSizeOfTag < sizeof(cmsUInt32Number)) goto error; + if (!_cmsReadUInt32Number(io, &CountBg)) goto error; SignedSizeOfTag -= sizeof(cmsUInt32Number); n ->Bg = cmsBuildTabulatedToneCurve16(self ->ContextID, CountBg, NULL); - if (n ->Bg == NULL) return NULL; + if (n ->Bg == NULL) goto error; - if (SignedSizeOfTag < (cmsInt32Number) CountBg * sizeof(cmsUInt16Number)) return NULL; - if (!_cmsReadUInt16Array(io, CountBg, n ->Bg->Table16)) return NULL; + if (SignedSizeOfTag < (cmsInt32Number) CountBg * sizeof(cmsUInt16Number)) goto error; + if (!_cmsReadUInt16Array(io, CountBg, n ->Bg->Table16)) goto error; SignedSizeOfTag -= CountBg * sizeof(cmsUInt16Number); - if (SignedSizeOfTag < 0 || SignedSizeOfTag > 32000) return NULL; + if (SignedSizeOfTag < 0 || SignedSizeOfTag > 32000) goto error; // Now comes the text. The length is specified by the tag size n ->Desc = cmsMLUalloc(self ->ContextID, 1); - if (n ->Desc == NULL) return NULL; + if (n ->Desc == NULL) goto error; ASCIIString = (char*) _cmsMalloc(self ->ContextID, SignedSizeOfTag + 1); - if (io ->Read(io, ASCIIString, sizeof(char), SignedSizeOfTag) != (cmsUInt32Number) SignedSizeOfTag) return NULL; + if (io->Read(io, ASCIIString, sizeof(char), SignedSizeOfTag) != (cmsUInt32Number)SignedSizeOfTag) + { + _cmsFree(self->ContextID, ASCIIString); + goto error; + } + ASCIIString[SignedSizeOfTag] = 0; cmsMLUsetASCII(n ->Desc, cmsNoLanguage, cmsNoCountry, ASCIIString); _cmsFree(self ->ContextID, ASCIIString); *nItems = 1; return (void*) n; + +error: + + if (n->Ucr) cmsFreeToneCurve(n->Ucr); + if (n->Bg) cmsFreeToneCurve(n->Bg); + if (n->Desc) cmsMLUfree(n->Desc); + _cmsFree(self->ContextID, n); + *nItems = 0; + return NULL; + } static @@ -5008,27 +5023,41 @@ cmsBool ReadOneElem(cmsIOHANDLER* io, _cmsDICelem* e, cmsUInt32Number i, cmsUIn static -cmsBool ReadOffsetArray(cmsIOHANDLER* io, _cmsDICarray* a, cmsUInt32Number Count, cmsUInt32Number Length, cmsUInt32Number BaseOffset) +cmsBool ReadOffsetArray(cmsIOHANDLER* io, _cmsDICarray* a, + cmsUInt32Number Count, cmsUInt32Number Length, cmsUInt32Number BaseOffset, + cmsInt32Number* SignedSizeOfTagPtr) { cmsUInt32Number i; + cmsInt32Number SignedSizeOfTag = *SignedSizeOfTagPtr; // Read column arrays for (i=0; i < Count; i++) { + if (SignedSizeOfTag < 4 * sizeof(cmsUInt32Number)) return FALSE; + SignedSizeOfTag -= 4 * sizeof(cmsUInt32Number); + if (!ReadOneElem(io, &a -> Name, i, BaseOffset)) return FALSE; if (!ReadOneElem(io, &a -> Value, i, BaseOffset)) return FALSE; if (Length > 16) { + if (SignedSizeOfTag < 2 * sizeof(cmsUInt32Number)) return FALSE; + SignedSizeOfTag -= 2 * sizeof(cmsUInt32Number); + if (!ReadOneElem(io, &a ->DisplayName, i, BaseOffset)) return FALSE; } if (Length > 24) { + if (SignedSizeOfTag < 2 * sizeof(cmsUInt32Number)) return FALSE; + SignedSizeOfTag -= 2 * sizeof(cmsUInt32Number); + if (!ReadOneElem(io, & a -> DisplayValue, i, BaseOffset)) return FALSE; } } + + *SignedSizeOfTagPtr = SignedSizeOfTag; return TRUE; } @@ -5176,26 +5205,31 @@ cmsBool WriteOneMLUC(struct _cms_typehandler_struct* self, cmsIOHANDLER* io, _c static void *Type_Dictionary_Read(struct _cms_typehandler_struct* self, cmsIOHANDLER* io, cmsUInt32Number* nItems, cmsUInt32Number SizeOfTag) { - cmsHANDLE hDict; + cmsHANDLE hDict = NULL; cmsUInt32Number i, Count, Length; cmsUInt32Number BaseOffset; _cmsDICarray a; wchar_t *NameWCS = NULL, *ValueWCS = NULL; cmsMLU *DisplayNameMLU = NULL, *DisplayValueMLU=NULL; cmsBool rc; + cmsInt32Number SignedSizeOfTag = (cmsInt32Number)SizeOfTag; *nItems = 0; + memset(&a, 0, sizeof(a)); // Get actual position as a basis for element offsets BaseOffset = io ->Tell(io) - sizeof(_cmsTagBase); // Get name-value record count + SignedSizeOfTag -= sizeof(cmsUInt32Number); + if (SignedSizeOfTag < 0) goto Error; if (!_cmsReadUInt32Number(io, &Count)) return NULL; - SizeOfTag -= sizeof(cmsUInt32Number); - + // Get rec length + SignedSizeOfTag -= sizeof(cmsUInt32Number); + if (SignedSizeOfTag < 0) goto Error; if (!_cmsReadUInt32Number(io, &Length)) return NULL; - SizeOfTag -= sizeof(cmsUInt32Number); + // Check for valid lengths if (Length != 16 && Length != 24 && Length != 32) { @@ -5211,7 +5245,7 @@ void *Type_Dictionary_Read(struct _cms_typehandler_struct* self, cmsIOHANDLER* i if (!AllocArray(self -> ContextID, &a, Count, Length)) goto Error; // Read column arrays - if (!ReadOffsetArray(io, &a, Count, Length, BaseOffset)) goto Error; + if (!ReadOffsetArray(io, &a, Count, Length, BaseOffset, &SignedSizeOfTag)) goto Error; // Seek to each element and read it for (i=0; i < Count; i++) { @@ -5251,7 +5285,7 @@ void *Type_Dictionary_Read(struct _cms_typehandler_struct* self, cmsIOHANDLER* i Error: FreeArray(&a); - cmsDictFree(hDict); + if (hDict != NULL) cmsDictFree(hDict); return NULL; } |