Bug 1468552 - Update bspatch.cpp to match Chromium version; r=rstrong

Adds bounds checking around file reads and header values

Differential Revision: https://phabricator.services.mozilla.com/D12356

--HG--
extra : moz-landing-system : lando
This commit is contained in:
June Wilde 2018-11-26 22:01:08 +00:00
Родитель 3dba77a779
Коммит 7b299ca4fc
1 изменённых файлов: 41 добавлений и 12 удалений

Просмотреть файл

@ -71,16 +71,33 @@ MBS_ReadHeader(FILE* file, MBSPatchHeader *header)
struct stat hs;
s = fstat(fileno(file), &hs);
if (s)
if (s != 0)
return READ_ERROR;
if (memcmp(header->tag, "MBDIFF10", 8) != 0)
return UNEXPECTED_BSPATCH_ERROR;
if (sizeof(MBSPatchHeader) +
header->cblen +
header->difflen +
header->extralen != uint32_t(hs.st_size))
if (hs.st_size > INT_MAX)
return UNEXPECTED_BSPATCH_ERROR;
size_t size = static_cast<size_t>(hs.st_size);
if (size < sizeof(MBSPatchHeader))
return UNEXPECTED_BSPATCH_ERROR;
size -= sizeof(MBSPatchHeader);
if (size < header->cblen)
return UNEXPECTED_BSPATCH_ERROR;
size -= header->cblen;
if (size < header->difflen)
return UNEXPECTED_BSPATCH_ERROR;
size -= header->difflen;
if (size < header->extralen)
return UNEXPECTED_BSPATCH_ERROR;
size -= header->extralen;
if (size != 0)
return UNEXPECTED_BSPATCH_ERROR;
return OK;
@ -90,6 +107,7 @@ int
MBS_ApplyPatch(const MBSPatchHeader *header, FILE* patchFile,
unsigned char *fbuffer, FILE* file)
{
unsigned char *fbufstart = fbuffer;
unsigned char *fbufend = fbuffer + header->slen;
unsigned char *buf = (unsigned char*) malloc(header->cblen +
@ -105,17 +123,27 @@ MBS_ApplyPatch(const MBSPatchHeader *header, FILE* patchFile,
while (r) {
const size_t count = (r > SSIZE_MAX) ? SSIZE_MAX : r;
size_t c = fread(wb, 1, count, patchFile);
if (c != count) {
if (c < 0 && c != count) {
rv = READ_ERROR;
goto end;
}
r -= c;
wb += c;
if (c == 0 && r) {
rv = UNEXPECTED_BSPATCH_ERROR;
goto end;
}
}
{
MBSPatchTriple *ctrlsrc = (MBSPatchTriple*) buf;
if (header->cblen % sizeof(MBSPatchTriple) != 0) {
rv = UNEXPECTED_BSPATCH_ERROR;
goto end;
}
unsigned char *diffsrc = buf + header->cblen;
unsigned char *extrasrc = diffsrc + header->difflen;
@ -123,7 +151,7 @@ MBS_ApplyPatch(const MBSPatchHeader *header, FILE* patchFile,
unsigned char *diffend = extrasrc;
unsigned char *extraend = extrasrc + header->extralen;
do {
while (ctrlsrc < ctrlend) {
ctrlsrc->x = ntohl(ctrlsrc->x);
ctrlsrc->y = ntohl(ctrlsrc->y);
ctrlsrc->z = ntohl(ctrlsrc->z);
@ -140,8 +168,8 @@ MBS_ApplyPatch(const MBSPatchHeader *header, FILE* patchFile,
/* Add x bytes from oldfile to x bytes from the diff block */
if (fbuffer + ctrlsrc->x > fbufend ||
diffsrc + ctrlsrc->x > diffend) {
if (ctrlsrc->x > static_cast<size_t>(fbufend - fbuffer) ||
ctrlsrc->x > static_cast<size_t>(diffend - diffsrc)) {
rv = UNEXPECTED_BSPATCH_ERROR;
goto end;
}
@ -157,7 +185,7 @@ MBS_ApplyPatch(const MBSPatchHeader *header, FILE* patchFile,
/* Copy y bytes from the extra block */
if (extrasrc + ctrlsrc->y > extraend) {
if (ctrlsrc->y > static_cast<size_t>(extraend - extrasrc)) {
rv = UNEXPECTED_BSPATCH_ERROR;
goto end;
}
@ -169,7 +197,8 @@ MBS_ApplyPatch(const MBSPatchHeader *header, FILE* patchFile,
/* "seek" forwards in oldfile by z bytes */
if (fbuffer + ctrlsrc->z > fbufend) {
if (ctrlsrc->z < fbufstart - fbuffer ||
ctrlsrc->z > fbufend - fbuffer) {
rv = UNEXPECTED_BSPATCH_ERROR;
goto end;
}
@ -178,7 +207,7 @@ MBS_ApplyPatch(const MBSPatchHeader *header, FILE* patchFile,
/* and on to the next control block */
++ctrlsrc;
} while (ctrlsrc < ctrlend);
}
}
end: