diff options
author | dgp <dgp@users.sourceforge.net> | 2014-04-14 18:45:04 (GMT) |
---|---|---|
committer | dgp <dgp@users.sourceforge.net> | 2014-04-14 18:45:04 (GMT) |
commit | 7b02be1867d1e46c5a4b5bc9f8925a4a6784c3fd (patch) | |
tree | ecf7be58520cfa947a7e80439acc6ff62f2d54a1 | |
parent | 7fb053c9643440e5075f5e513853c9efff0ae44d (diff) | |
download | tcl-7b02be1867d1e46c5a4b5bc9f8925a4a6784c3fd.zip tcl-7b02be1867d1e46c5a4b5bc9f8925a4a6784c3fd.tar.gz tcl-7b02be1867d1e46c5a4b5bc9f8925a4a6784c3fd.tar.bz2 |
[e663138a06] Fix the new INST_NUM_TYPE instruction so that the boundary
cases of [string is] on integral values are computed right. Code is now
correct, though still suffers from a large amount of ugly.
-rw-r--r-- | generic/tclExecute.c | 28 |
1 files changed, 22 insertions, 6 deletions
diff --git a/generic/tclExecute.c b/generic/tclExecute.c index 6394a60..2c136d7 100644 --- a/generic/tclExecute.c +++ b/generic/tclExecute.c @@ -5989,16 +5989,32 @@ TEBCresume( case INST_NUM_TYPE: if (GetNumberFromObj(NULL, OBJ_AT_TOS, &ptr1, &type1) != TCL_OK) { type1 = 0; - } + } else if (type1 == TCL_NUMBER_LONG) { + /* value is between LONG_MIN and LONG_MAX */ + /* [string is integer] is -UINT_MAX to UINT_MAX range */ + int i; + + if (Tcl_GetIntFromObj(NULL, OBJ_AT_TOS, &i) != TCL_OK) { + type1 = TCL_NUMBER_WIDE; + } #ifndef TCL_WIDE_INT_IS_LONG - else if (type1 == TCL_NUMBER_WIDE) { - /** See bug [e663138a06] */ - Tcl_WideInt value = (OBJ_AT_TOS)->internalRep.wideValue; - if ((-value <= ULONG_MAX) && (value <= ULONG_MAX)) { + } else if (type1 == TCL_NUMBER_WIDE) { + /* value is between WIDE_MIN and WIDE_MAX */ + /* [string is wideinteger] is -UWIDE_MAX to UWIDE_MAX range */ + int i; + if (Tcl_GetIntFromObj(NULL, OBJ_AT_TOS, &i) == TCL_OK) { type1 = TCL_NUMBER_LONG; } - } #endif + } else if (type1 == TCL_NUMBER_BIG) { + /* value is an integer outside the WIDE_MIN to WIDE_MAX range */ + /* [string is wideinteger] is -UWIDE_MAX to UWIDE_MAX range */ + Tcl_WideInt w; + + if (Tcl_GetWideIntFromObj(NULL, OBJ_AT_TOS, &w) == TCL_OK) { + type1 = TCL_NUMBER_WIDE; + } + } TclNewIntObj(objResultPtr, type1); TRACE(("\"%.20s\" => %d\n", O2S(OBJ_AT_TOS), type1)); NEXT_INST_F(1, 1, 1); |