summaryrefslogtreecommitdiffstats
path: root/generic/tclStringObj.c
diff options
context:
space:
mode:
authordgp <dgp@users.sourceforge.net>2018-07-26 16:14:44 (GMT)
committerdgp <dgp@users.sourceforge.net>2018-07-26 16:14:44 (GMT)
commit76334501285b373e97461a7a8215bdf961ddd384 (patch)
tree0493cca44a9fa057af82b17ba819c21a3dc5b159 /generic/tclStringObj.c
parent54fbd7dbcb9247399d2ac512e9d5bc305114dd58 (diff)
parent164a7f04c03e56a310d9386fd8ddbd6319c0c788 (diff)
downloadtcl-76334501285b373e97461a7a8215bdf961ddd384.zip
tcl-76334501285b373e97461a7a8215bdf961ddd384.tar.gz
tcl-76334501285b373e97461a7a8215bdf961ddd384.tar.bz2
[ba921a8d98] Make sure [string cat] includes all data from all bytearrays.
Diffstat (limited to 'generic/tclStringObj.c')
-rw-r--r--generic/tclStringObj.c32
1 files changed, 23 insertions, 9 deletions
diff --git a/generic/tclStringObj.c b/generic/tclStringObj.c
index 2cda2c4..767026d 100644
--- a/generic/tclStringObj.c
+++ b/generic/tclStringObj.c
@@ -3071,16 +3071,24 @@ TclStringCat(
do {
Tcl_Obj *objPtr = *ov++;
- Tcl_GetByteArrayFromObj(objPtr, &numBytes); /* PANIC? */
+ /*
+ * Every argument is either a bytearray with a ("pure")
+ * value we know we can safely use, or it is an empty string.
+ * We don't need to count bytes for the empty strings.
+ */
- if (numBytes) {
- last = objc - oc;
- if (length == 0) {
- first = last;
- } else if (numBytes > INT_MAX - length) {
- goto overflow;
+ if (TclIsPureByteArray(objPtr)) {
+ Tcl_GetByteArrayFromObj(objPtr, &numBytes); /* PANIC? */
+
+ if (numBytes) {
+ last = objc - oc;
+ if (length == 0) {
+ first = last;
+ } else if (numBytes > INT_MAX - length) {
+ goto overflow;
+ }
+ length += numBytes;
}
- length += numBytes;
}
} while (--oc);
} else if (allowUniChar && requestUniChar) {
@@ -3223,7 +3231,13 @@ TclStringCat(
while (objc--) {
Tcl_Obj *objPtr = *objv++;
- if (objPtr->bytes == NULL) {
+ /*
+ * Every argument is either a bytearray with a ("pure")
+ * value we know we can safely use, or it is an empty string.
+ * We don't need to copy bytes from the empty strings.
+ */
+
+ if (TclIsPureByteArray(objPtr)) {
int more;
unsigned char *src = Tcl_GetByteArrayFromObj(objPtr, &more);
memcpy(dst, src, (size_t) more);