diff options
| author | jan.nijtmans <nijtmans@users.sourceforge.net> | 2021-02-17 16:16:19 (GMT) |
|---|---|---|
| committer | jan.nijtmans <nijtmans@users.sourceforge.net> | 2021-02-17 16:16:19 (GMT) |
| commit | 28d58d74b0e3837b5ca9c2020bd14cf21ee98a41 (patch) | |
| tree | b193046e1224edc0889b6a7981b4a31dc5b6a903 | |
| parent | 6067ce5573215928878a619b512a6cf06ab4690e (diff) | |
| download | tcl-28d58d74b0e3837b5ca9c2020bd14cf21ee98a41.zip tcl-28d58d74b0e3837b5ca9c2020bd14cf21ee98a41.tar.gz tcl-28d58d74b0e3837b5ca9c2020bd14cf21ee98a41.tar.bz2 | |
Fix abs(-9223372036854775808) special-case on platforms where sizeof(Tcl_WideInt) > sizeof(int64_t). Theoretical, yes, but at least add a testcase for this (expr-38.14)
| -rw-r--r-- | generic/tclBasic.c | 11 | ||||
| -rw-r--r-- | tests/expr.test | 3 |
2 files changed, 13 insertions, 1 deletions
diff --git a/generic/tclBasic.c b/generic/tclBasic.c index 2ed4270..b2d3f28 100644 --- a/generic/tclBasic.c +++ b/generic/tclBasic.c @@ -7906,7 +7906,16 @@ ExprAbsFunc( } goto unChanged; } else if (l == WIDE_MIN) { - if (mp_init_i64(&big, l) != MP_OKAY) { + if (sizeof(Tcl_WideInt) > sizeof(int64_t)) { + Tcl_WideUInt ul = -(Tcl_WideUInt)WIDE_MIN; + if (mp_init(&big) != MP_OKAY || mp_unpack(&big, 1, 1, + sizeof(Tcl_WideInt), 0, 0, &ul) != MP_OKAY) { + return TCL_ERROR; + } + if (mp_neg(&big, &big) != MP_OKAY) { + return TCL_ERROR; + } + } else if (mp_init_i64(&big, l) != MP_OKAY) { return TCL_ERROR; } goto tooLarge; diff --git a/tests/expr.test b/tests/expr.test index 9add1f1..5435a18 100644 --- a/tests/expr.test +++ b/tests/expr.test @@ -6699,6 +6699,9 @@ test expr-38.12 {abs and -0x0 [Bug 2954959]} { test expr-38.13 {abs and 0.0 [Bug 2954959]} { ::tcl::mathfunc::abs 1e-324 } 1e-324 +test expr-38.14 {abs and WIDE_MIN special-case} { + ::tcl::mathfunc::abs -9223372036854775808 +} 9223372036854775808 testConstraint testexprlongobj [llength [info commands testexprlongobj]] testConstraint testexprdoubleobj [llength [info commands testexprdoubleobj]] |
