| Index: nspr/pr/src/io/prprf.c
|
| diff --git a/nspr/pr/src/io/prprf.c b/nspr/pr/src/io/prprf.c
|
| index 1a89141548286b2ca37137ce100c922471593ce8..798ea2a448b091e3854cd3a7f3407236336e31dc 100644
|
| --- a/nspr/pr/src/io/prprf.c
|
| +++ b/nspr/pr/src/io/prprf.c
|
| @@ -37,7 +37,7 @@ struct SprintfStateStr {
|
|
|
| char *base;
|
| char *cur;
|
| - PRUint32 maxlen;
|
| + PRUint32 maxlen; /* Must not exceed PR_INT32_MAX. */
|
|
|
| int (*func)(void *arg, const char *sp, PRUint32 len);
|
| void *arg;
|
| @@ -697,7 +697,7 @@ static int dosprintf(SprintfState *ss, const char *fmt, va_list ap)
|
| char *hexp;
|
| int rv, i;
|
| struct NumArg* nas = NULL;
|
| - struct NumArg* nap;
|
| + struct NumArg* nap = NULL;
|
| struct NumArg nasArray[ NAS_DEFAULT_NUM ];
|
| char pattern[20];
|
| const char* dolPt = NULL; /* in "%4$.2f", dolPt will point to . */
|
| @@ -1060,6 +1060,13 @@ static int FuncStuff(SprintfState *ss, const char *sp, PRUint32 len)
|
| {
|
| int rv;
|
|
|
| + /*
|
| + ** We will add len to ss->maxlen at the end of the function. First check
|
| + ** if ss->maxlen + len would overflow or be greater than PR_INT32_MAX.
|
| + */
|
| + if (PR_UINT32_MAX - ss->maxlen < len || ss->maxlen + len > PR_INT32_MAX) {
|
| + return -1;
|
| + }
|
| rv = (*ss->func)(ss->arg, sp, len);
|
| if (rv < 0) {
|
| return rv;
|
| @@ -1105,9 +1112,21 @@ static int GrowStuff(SprintfState *ss, const char *sp, PRUint32 len)
|
| PRUint32 newlen;
|
|
|
| off = ss->cur - ss->base;
|
| + if (PR_UINT32_MAX - len < off) {
|
| + /* off + len would be too big. */
|
| + return -1;
|
| + }
|
| if (off + len >= ss->maxlen) {
|
| /* Grow the buffer */
|
| - newlen = ss->maxlen + ((len > 32) ? len : 32);
|
| + PRUint32 increment = (len > 32) ? len : 32;
|
| + if (PR_UINT32_MAX - ss->maxlen < increment) {
|
| + /* ss->maxlen + increment would overflow. */
|
| + return -1;
|
| + }
|
| + newlen = ss->maxlen + increment;
|
| + if (newlen > PR_INT32_MAX) {
|
| + return -1;
|
| + }
|
| if (ss->base) {
|
| newbase = (char*) PR_REALLOC(ss->base, newlen);
|
| } else {
|
| @@ -1210,8 +1229,8 @@ PR_IMPLEMENT(PRUint32) PR_vsnprintf(char *out, PRUint32 outlen,const char *fmt,
|
| SprintfState ss;
|
| PRUint32 n;
|
|
|
| - PR_ASSERT((PRInt32)outlen > 0);
|
| - if ((PRInt32)outlen <= 0) {
|
| + PR_ASSERT(outlen != 0 && outlen <= PR_INT32_MAX);
|
| + if (outlen == 0 || outlen > PR_INT32_MAX) {
|
| return 0;
|
| }
|
|
|
| @@ -1247,7 +1266,10 @@ PR_IMPLEMENT(char *) PR_vsprintf_append(char *last, const char *fmt, va_list ap)
|
|
|
| ss.stuff = GrowStuff;
|
| if (last) {
|
| - int lastlen = strlen(last);
|
| + size_t lastlen = strlen(last);
|
| + if (lastlen > PR_INT32_MAX) {
|
| + return 0;
|
| + }
|
| ss.base = last;
|
| ss.cur = last + lastlen;
|
| ss.maxlen = lastlen;
|
|
|