aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTatsuya Kinoshita <tats@debian.org>2021-03-02 10:48:39 +0000
committerTatsuya Kinoshita <tats@debian.org>2021-03-02 10:48:39 +0000
commit2b68bdf4ba57e052b41cbfe6349deb2b0a401442 (patch)
treee509374480e1a7a60a2453b35f9d89b0df7bfdc6
parentMerge pull request #170 from bptato/master (diff)
downloadw3m-2b68bdf4ba57e052b41cbfe6349deb2b0a401442.tar.gz
w3m-2b68bdf4ba57e052b41cbfe6349deb2b0a401442.zip
Prevent large memory usage and null-deref in Str.c
Bug-Chromium: https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=31579 Bug-Chromium: https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=31589
-rw-r--r--Str.c28
1 files changed, 27 insertions, 1 deletions
diff --git a/Str.c b/Str.c
index 03e0950..0786ec1 100644
--- a/Str.c
+++ b/Str.c
@@ -26,7 +26,7 @@
#include "myctype.h"
#define INITIAL_STR_SIZE 32
-#define STR_SIZE_MAX (INT_MAX - 1)
+#define STR_SIZE_MAX (INT_MAX / 8)
#ifdef STR_DEBUG
/* This is obsolete, because "Str" can handle a '\0' character now. */
@@ -39,7 +39,11 @@ Str
Strnew()
{
Str x = GC_MALLOC(sizeof(struct _Str));
+ if (x == NULL)
+ exit(1);
x->ptr = GC_MALLOC_ATOMIC(INITIAL_STR_SIZE);
+ if (x->ptr == NULL)
+ exit(1);
x->ptr[0] = '\0';
x->area_size = INITIAL_STR_SIZE;
x->length = 0;
@@ -50,9 +54,13 @@ Str
Strnew_size(int n)
{
Str x = GC_MALLOC(sizeof(struct _Str));
+ if (x == NULL)
+ exit(1);
if (n < 0 || n >= STR_SIZE_MAX)
n = STR_SIZE_MAX - 1;
x->ptr = GC_MALLOC_ATOMIC(n + 1);
+ if (x->ptr == NULL)
+ exit(1);
x->ptr[0] = '\0';
x->area_size = n + 1;
x->length = 0;
@@ -68,10 +76,14 @@ Strnew_charp(const char *p)
if (p == NULL)
return Strnew();
x = GC_MALLOC(sizeof(struct _Str));
+ if (x == NULL)
+ exit(1);
n = strlen(p) + 1;
if (n <= 0 || n > STR_SIZE_MAX)
n = STR_SIZE_MAX;
x->ptr = GC_MALLOC_ATOMIC(n);
+ if (x->ptr == NULL)
+ exit(1);
x->area_size = n;
x->length = n - 1;
bcopy((void *)p, (void *)x->ptr, n - 1);
@@ -101,9 +113,13 @@ Strnew_charp_n(const char *p, int n)
if (p == NULL)
return Strnew_size(n);
x = GC_MALLOC(sizeof(struct _Str));
+ if (x == NULL)
+ exit(1);
if (n < 0 || n >= STR_SIZE_MAX)
n = STR_SIZE_MAX - 1;
x->ptr = GC_MALLOC_ATOMIC(n + 1);
+ if (x->ptr == NULL)
+ exit(1);
x->area_size = n + 1;
x->length = n;
bcopy((void *)p, (void *)x->ptr, n);
@@ -142,6 +158,8 @@ Strcopy(Str x, Str y)
if (x->area_size < y->length + 1) {
GC_free(x->ptr);
x->ptr = GC_MALLOC_ATOMIC(y->length + 1);
+ if (x->ptr == NULL)
+ exit(1);
x->area_size = y->length + 1;
}
bcopy((void *)y->ptr, (void *)x->ptr, y->length + 1);
@@ -165,6 +183,8 @@ Strcopy_charp(Str x, const char *y)
if (x->area_size < len + 1) {
GC_free(x->ptr);
x->ptr = GC_MALLOC_ATOMIC(len + 1);
+ if (x->ptr == NULL)
+ exit(1);
x->area_size = len + 1;
}
bcopy((void *)y, (void *)x->ptr, len);
@@ -188,6 +208,8 @@ Strcopy_charp_n(Str x, const char *y, int n)
if (x->area_size < len + 1) {
GC_free(x->ptr);
x->ptr = GC_MALLOC_ATOMIC(len + 1);
+ if (x->ptr == NULL)
+ exit(1);
x->area_size = len + 1;
}
bcopy((void *)y, (void *)x->ptr, len);
@@ -216,6 +238,8 @@ Strcat_charp_n(Str x, const char *y, int n)
if (newlen <= 0 || newlen > STR_SIZE_MAX)
newlen = STR_SIZE_MAX;
x->ptr = GC_MALLOC_ATOMIC(newlen);
+ if (x->ptr == NULL)
+ exit(1);
x->area_size = newlen;
bcopy((void *)old, (void *)x->ptr, x->length);
GC_free(old);
@@ -265,6 +289,8 @@ Strgrow(Str x)
x->length = newlen - 2;
}
x->ptr = GC_MALLOC_ATOMIC(newlen);
+ if (x->ptr == NULL)
+ exit(1);
x->area_size = newlen;
bcopy((void *)old, (void *)x->ptr, x->length);
x->ptr[x->length] = '\0';