bug 918265 - deal with long www-authenticate fields r=sworkman

--HG--
extra : rebase_source : 55e06159aa7f6464c07d3736580af26090a87179
This commit is contained in:
Patrick McManus 2013-09-26 14:54:59 -04:00
parent 862868d7df
commit 7ee039acef
2 changed files with 1499 additions and 7 deletions

View File

@ -537,6 +537,12 @@ nsHttpDigestAuth::ParseChallenge(const char * challenge,
uint16_t * algorithm, uint16_t * algorithm,
uint16_t * qop) uint16_t * qop)
{ {
// put an absurd, but maximum, length cap on the challenge so
// that calculations are 32 bit safe
if (strlen(challenge) > 16000000) {
return NS_ERROR_INVALID_ARG;
}
const char *p = challenge + 7; // first 7 characters are "Digest " const char *p = challenge + 7; // first 7 characters are "Digest "
*stale = false; *stale = false;
@ -550,12 +556,12 @@ nsHttpDigestAuth::ParseChallenge(const char * challenge,
break; break;
// name // name
int16_t nameStart = (p - challenge); int32_t nameStart = (p - challenge);
while (*p && !nsCRT::IsAsciiSpace(*p) && *p != '=') while (*p && !nsCRT::IsAsciiSpace(*p) && *p != '=')
++p; ++p;
if (!*p) if (!*p)
return NS_ERROR_INVALID_ARG; return NS_ERROR_INVALID_ARG;
int16_t nameLength = (p - challenge) - nameStart; int32_t nameLength = (p - challenge) - nameStart;
while (*p && (nsCRT::IsAsciiSpace(*p) || *p == '=')) while (*p && (nsCRT::IsAsciiSpace(*p) || *p == '='))
++p; ++p;
@ -569,8 +575,8 @@ nsHttpDigestAuth::ParseChallenge(const char * challenge,
} }
// value // value
int16_t valueStart = (p - challenge); int32_t valueStart = (p - challenge);
int16_t valueLength = 0; int32_t valueLength = 0;
if (quoted) { if (quoted) {
while (*p && *p != '"') while (*p && *p != '"')
++p; ++p;
@ -628,13 +634,13 @@ nsHttpDigestAuth::ParseChallenge(const char * challenge,
else if (nameLength == 3 && else if (nameLength == 3 &&
nsCRT::strncasecmp(challenge+nameStart, "qop", 3) == 0) nsCRT::strncasecmp(challenge+nameStart, "qop", 3) == 0)
{ {
int16_t ipos = valueStart; int32_t ipos = valueStart;
while (ipos < valueStart+valueLength) { while (ipos < valueStart+valueLength) {
while (ipos < valueStart+valueLength && while (ipos < valueStart+valueLength &&
(nsCRT::IsAsciiSpace(challenge[ipos]) || (nsCRT::IsAsciiSpace(challenge[ipos]) ||
challenge[ipos] == ',')) challenge[ipos] == ','))
ipos++; ipos++;
int16_t algostart = ipos; int32_t algostart = ipos;
while (ipos < valueStart+valueLength && while (ipos < valueStart+valueLength &&
!nsCRT::IsAsciiSpace(challenge[ipos]) && !nsCRT::IsAsciiSpace(challenge[ipos]) &&
challenge[ipos] != ',') challenge[ipos] != ',')

File diff suppressed because it is too large Load Diff