summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authordgp <dgp@users.sourceforge.net>2022-03-11 20:56:53 (GMT)
committerdgp <dgp@users.sourceforge.net>2022-03-11 20:56:53 (GMT)
commitfaf6b59bc281418a6a1cdf37dbee88c7fbd2429b (patch)
tree7d75fc9da47f8725334e2864c8a18b1db4373fef
parent15cbaf50c0120388c16c0dab87e650c3f9c40ea1 (diff)
downloadtcl-faf6b59bc281418a6a1cdf37dbee88c7fbd2429b.zip
tcl-faf6b59bc281418a6a1cdf37dbee88c7fbd2429b.tar.gz
tcl-faf6b59bc281418a6a1cdf37dbee88c7fbd2429b.tar.bz2
Update overflow protections to the size_t type.
-rw-r--r--generic/tclBinary.c40
1 files changed, 21 insertions, 19 deletions
diff --git a/generic/tclBinary.c b/generic/tclBinary.c
index dd8bbc0..1955d85 100644
--- a/generic/tclBinary.c
+++ b/generic/tclBinary.c
@@ -183,7 +183,9 @@ typedef struct {
} ByteArray;
#define BYTEARRAY_SIZE(len) \
- (offsetof(ByteArray, bytes) + (len))
+ ( (offsetof(ByteArray, bytes) + (len) < offsetof(ByteArray, bytes)) \
+ ? (Tcl_Panic("max size of a Tcl value exceeded"), 0) \
+ : (offsetof(ByteArray, bytes) + (len)) )
#define GET_BYTEARRAY(irPtr) ((ByteArray *) (irPtr)->twoPtrValue.ptr1)
#define SET_BYTEARRAY(irPtr, baPtr) \
(irPtr)->twoPtrValue.ptr1 = (baPtr)
@@ -785,31 +787,28 @@ TclAppendBytesToByteArray(
}
byteArrayPtr = GET_BYTEARRAY(irPtr);
- /* Size limit check now commented out. Used to protect calls to
- * Tcl_*Alloc*() limited by unsigned int arguments.
- *
- if (len > UINT_MAX - byteArrayPtr->used) {
- Tcl_Panic("max size for a Tcl value (%u bytes) exceeded", UINT_MAX);
- }
- *
- */
-
- needed = byteArrayPtr->used + len;
/*
* If we need to, resize the allocated space in the byte array.
*/
+ needed = byteArrayPtr->used + len;
+ if (needed < byteArrayPtr->used) {
+ /* Wrapped around SIZE_MAX!! */
+ Tcl_Panic("max size of a Tcl value exceeded");
+ }
if (needed > byteArrayPtr->allocated) {
ByteArray *ptr = NULL;
- size_t attempt;
- if (needed <= INT_MAX/2) {
- /*
- * Try to allocate double the total space that is needed.
- */
+ /*
+ * Try to allocate double the total space that is needed.
+ */
- attempt = 2 * needed;
- ptr = (ByteArray *)Tcl_AttemptRealloc(byteArrayPtr, BYTEARRAY_SIZE(attempt));
+ size_t attempt = 2 * needed;
+
+ /* Protection just in case we wrapped around SIZE_MAX */
+ if (attempt >= needed) {
+ ptr = (ByteArray *) Tcl_AttemptRealloc(byteArrayPtr,
+ BYTEARRAY_SIZE(attempt));
}
if (ptr == NULL) {
/*
@@ -817,7 +816,10 @@ TclAppendBytesToByteArray(
*/
attempt = needed + len + TCL_MIN_GROWTH;
- ptr = (ByteArray *)Tcl_AttemptRealloc(byteArrayPtr, BYTEARRAY_SIZE(attempt));
+ if (attempt >= needed) {
+ ptr = (ByteArray *) Tcl_AttemptRealloc(byteArrayPtr,
+ BYTEARRAY_SIZE(attempt));
+ }
}
if (ptr == NULL) {
/*