summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--generic/tclStringObj.c4
-rw-r--r--tests/format.test14
2 files changed, 18 insertions, 0 deletions
diff --git a/generic/tclStringObj.c b/generic/tclStringObj.c
index 1795d0c..3139be4 100644
--- a/generic/tclStringObj.c
+++ b/generic/tclStringObj.c
@@ -1876,6 +1876,10 @@ Tcl_AppendFormatToObj(
width = 0;
if (isdigit(UCHAR(ch))) {
width = strtoul(format, &end, 10);
+ if (width < 0) {
+ msg = overflow;
+ goto errorMsg;
+ }
format = end;
step = TclUtfToUniChar(format, &ch);
} else if (ch == '*') {
diff --git a/tests/format.test b/tests/format.test
index 2795ac2..88013cf 100644
--- a/tests/format.test
+++ b/tests/format.test
@@ -585,6 +585,20 @@ test format-19.3 {Bug 2830354} {
string length [format %340f 0]
} 340
+test format-19.4.1 {Bug d498578df4: width overflow should cause limit exceeded} \
+-constraints {longIs32bit} -body {
+ # in case of overflow into negative, it produces width -2 (and limit exceeded),
+ # in case of width will be unsigned, it will be outside limit (2GB for 32bit)...
+ # and it don't throw an error in case the bug is not fixed (and probably no segfault).
+ format %[expr {0xffffffff - 1}]g 0
+} -returnCodes error -result "max size for a Tcl value exceeded"
+
+test format-19.4.2 {Bug d498578df4: width overflow should cause limit exceeded} -body {
+ # limit should exceeds in any case,
+ # and it don't throw an error in case the bug is not fixed (and probably no segfault).
+ format %[expr {0xffffffffffffffff - 1}]g 0
+} -returnCodes error -result "max size for a Tcl value exceeded"
+
# Note that this test may fail in future versions
test format-20.1 {Bug 2932421: plain %s caused intrep change of args} -body {
set x [dict create a b c d]