Changeset: 4e1010b8b745 for MonetDB
URL: http://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=4e1010b8b745
Modified Files:
monetdb5/modules/atoms/str.c
Branch: Jul2017
Log Message:
Fix out-of-bounds write (found by sanitizer).
Also, don't use memmove to copy overlapping memory if that's not needed.
diffs (56 lines):
diff --git a/monetdb5/modules/atoms/str.c b/monetdb5/modules/atoms/str.c
--- a/monetdb5/modules/atoms/str.c
+++ b/monetdb5/modules/atoms/str.c
@@ -2340,30 +2340,39 @@ STRSubstitute(str *res, const str *arg1,
int repeat = *g;
size_t lsrc = src ? strlen(src) : 0;
size_t ldst = dst ? strlen(dst) : 0;
- size_t l = s ? strLen(s) : 0;
- size_t n = l + ldst;
- str buf, fnd, end;
+ size_t l = strLen(s);
+ size_t n;
+ char *buf;
+ const char *pfnd;
+ char *fnd;
+ if (s == NULL || strcmp(s, str_nil) == 0) {
+ if ((*res = GDKstrdup(str_nil)) == NULL)
+ throw(MAL, "str.substitute", MAL_MALLOC_FAIL);
+ return MAL_SUCCEED;
+ }
+
+ n = l + ldst;
if (repeat && ldst > lsrc && lsrc) {
n = (ldst * l) / lsrc; /* max length */
}
buf = *res = GDKmalloc(n);
if (*res == NULL)
throw(MAL, "str.substitute", MAL_MALLOC_FAIL);
- end = buf + l;
- fnd = buf;
- strcpy(buf, s ? s : "");
- if (lsrc == 0)
- return MAL_SUCCEED;
+
+ pfnd = s;
do {
- fnd = strstr(fnd < buf ? buf : fnd, src);
+ fnd = strstr(pfnd, src);
if (fnd == NULL)
break;
- memmove(fnd + ldst, fnd + lsrc, end - fnd);
- memcpy(fnd, dst, ldst);
- end += ldst - lsrc;
- fnd += ldst;
+ n = fnd - pfnd;
+ strncpy(buf, pfnd, n);
+ buf += n;
+ strncpy(buf, dst, ldst);
+ buf += ldst;
+ pfnd = fnd + lsrc;
} while (repeat);
+ strcpy(buf, pfnd);
return MAL_SUCCEED;
}
_______________________________________________
checkin-list mailing list
[email protected]
https://www.monetdb.org/mailman/listinfo/checkin-list