summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authordkf <donal.k.fellows@manchester.ac.uk>2005-06-01 10:02:06 (GMT)
committerdkf <donal.k.fellows@manchester.ac.uk>2005-06-01 10:02:06 (GMT)
commit8f397c357860e5098e4eeea5140ed0d3c724075d (patch)
tree309f612d31031e225f495a61bdf8b30f3b4601ed
parentf1f50f7c10e4e06c7dd7e75798a1475c376b6269 (diff)
downloadtcl-8f397c357860e5098e4eeea5140ed0d3c724075d.zip
tcl-8f397c357860e5098e4eeea5140ed0d3c724075d.tar.gz
tcl-8f397c357860e5098e4eeea5140ed0d3c724075d.tar.bz2
Increase efficiency of [lindex] compilation
-rw-r--r--ChangeLog3
-rw-r--r--generic/tclCompCmds.c35
2 files changed, 35 insertions, 3 deletions
diff --git a/ChangeLog b/ChangeLog
index 9ea2b3f..b00587a 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,8 @@
2005-06-01 Donal K. Fellows <donal.k.fellows@man.ac.uk>
+ * generic/tclCompCmds.c (TclCompileLindexCmd): Compile the most
+ common case of [lindex] more efficiently.
+
* unix/tclUnixNotfy.c (Tcl_FinalizeNotifier): Pass the correct
number of arguments to Tcl_JoinThread.
diff --git a/generic/tclCompCmds.c b/generic/tclCompCmds.c
index da77439..c412329 100644
--- a/generic/tclCompCmds.c
+++ b/generic/tclCompCmds.c
@@ -11,7 +11,7 @@
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
- * RCS: @(#) $Id: tclCompCmds.c,v 1.68 2005/05/10 18:34:09 kennykb Exp $
+ * RCS: @(#) $Id: tclCompCmds.c,v 1.69 2005/06/01 10:02:19 dkf Exp $
*/
#include "tclInt.h"
@@ -1711,7 +1711,36 @@ TclCompileLindexCmd(interp, parsePtr, envPtr)
}
varTokenPtr = parsePtr->tokenPtr
- + (parsePtr->tokenPtr->numComponents + 1);
+ + (parsePtr->tokenPtr->numComponents + 1);
+
+ if ((numWords == 3) && (varTokenPtr->type == TCL_TOKEN_SIMPLE_WORD) &&
+ TclLooksLikeInt(varTokenPtr[1].start, varTokenPtr[1].size)) {
+ Tcl_Obj *tmpObj;
+ int idx;
+
+ tmpObj = Tcl_NewStringObj(varTokenPtr[1].start, varTokenPtr[1].size);
+ if (Tcl_GetIntFromObj(NULL, tmpObj, &idx) == TCL_OK && idx >= 0) {
+ TclDecrRefCount(tmpObj);
+ varTokenPtr += varTokenPtr->numComponents + 1;
+ /*
+ * All checks have been completed, and we have exactly
+ * this construct:
+ * lindex <posInt> <arbitraryValue>
+ * This is best compiled as a push of the arbitrary value
+ * followed by an "immediate lindex" which is the most
+ * efficient variety.
+ */
+ CompileWord(envPtr, varTokenPtr, interp);
+ TclEmitInstInt4(INST_LIST_INDEX_IMM, idx, envPtr);
+ return TCL_OK;
+ } else {
+ /*
+ * If the conversion failed or the value was negative, we
+ * just keep on going with the more complex compilation.
+ */
+ TclDecrRefCount(tmpObj);
+ }
+ }
/*
* Push the operands onto the stack.
@@ -1719,7 +1748,7 @@ TclCompileLindexCmd(interp, parsePtr, envPtr)
for (i=1 ; i<numWords ; i++) {
CompileWord(envPtr, varTokenPtr, interp);
- varTokenPtr = varTokenPtr + (varTokenPtr->numComponents + 1);
+ varTokenPtr += varTokenPtr->numComponents + 1;
}
/*