]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Add the capability to track the maximum depth of the LALR(1) parser stack
authordrh <drh@noemail.net>
Fri, 25 Jul 2008 15:39:03 +0000 (15:39 +0000)
committerdrh <drh@noemail.net>
Fri, 25 Jul 2008 15:39:03 +0000 (15:39 +0000)
so that critical applications can check to see if they are getting close
to limits. (CVS 5481)

FossilOrigin-Name: ef0250f3dc769a4acd534f31fa06d90922d4145b

manifest
manifest.uuid
src/sqlite.h.in
src/sqliteInt.h
src/status.c
src/test_config.c
src/test_malloc.c
src/tokenize.c
test/tester.tcl
tool/lempar.c

index ce57c9bd49ccb1bc6b04410a801fd720e38d6d0f..44df1dd219e98cb562a9e12cda35382ab4cf8417 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Fix\sthe\scorrupt7\stests\sto\strack\schanges\sin\sthe\sintegrity\scheck\serror\smessage.\s(CVS\s5480)
-D 2008-07-25T14:53:17
+C Add\sthe\scapability\sto\strack\sthe\smaximum\sdepth\sof\sthe\sLALR(1)\sparser\sstack\nso\sthat\scritical\sapplications\scan\scheck\sto\ssee\sif\sthey\sare\sgetting\sclose\nto\slimits.\s(CVS\s5481)
+D 2008-07-25T15:39:04
 F Makefile.arm-wince-mingw32ce-gcc fcd5e9cd67fe88836360bb4f9ef4cb7f8e2fb5a0
 F Makefile.in d677b8dbc24fd815043e87e9350f8d296ab40f0d
 F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654
@@ -144,11 +144,11 @@ F src/printf.c 2174222bc346a11b1eac2a654ccc4f635355ae7e
 F src/random.c 5c754319d38abdd6acd74601ee0105504adc508a
 F src/select.c a152b1436d7117e25ce010453c61d1002214e337
 F src/shell.c 4b835fe734304ac22a3385868cd3790c1e4f7aa1
-F src/sqlite.h.in db24c33101337693d5930da8d31b0ca21e266447
+F src/sqlite.h.in dd72570543919552b62dcfbc24a93d8e5a46742e
 F src/sqlite3ext.h 1e3887c9bd3ae66cb599e922824b04cd0d0f2c3e
-F src/sqliteInt.h 17ada799d10670e20eb8549b848ca622b2e8bc26
+F src/sqliteInt.h f9036237debe48d3542595fae2a18dcb41cd71e9
 F src/sqliteLimit.h f435e728c6b620ef7312814d660a81f9356eb5c8
-F src/status.c 2076bc996618b1a112a797f05c1d62026ae01402
+F src/status.c 0f72b854aa75bb209718e0bb37728602c7ecdee6
 F src/table.c 22744786199c9195720c15a7a42cb97b2e2728d8
 F src/tclsqlite.c ec46084184f033ba396a9ee7b5514b695083d0f3
 F src/test1.c 346e9262793be825ebadd9e69600d1b4682650f1
@@ -163,12 +163,12 @@ F src/test9.c 904ebe0ed1472d6bad17a81e2ecbfc20017dc237
 F src/test_async.c da9f58f49faccd3a26ba89f58de125862351b6e2
 F src/test_autoext.c f53b0cdf7bf5f08100009572a5d65cdb540bd0ad
 F src/test_btree.c 7170e0c922ed3979f2d38f4a3f84728e5740dfc3
-F src/test_config.c 7d3c3bb37e12d8ed22c5e0900e1361178b0580a3
+F src/test_config.c 7896095e9af6e3fad0e42666880afdadfbd563ac
 F src/test_devsym.c 6012cb8e3acf812513511025a4fa5d626e0ba19b
 F src/test_func.c 24a556989685495013e08f311ae31c4ef86ddb8c
 F src/test_hexio.c 2f1122aa3f012fa0142ee3c36ce5c902a70cd12f
 F src/test_loadext.c df8ab3a6481ddebbdf0d28ebac5d9e0790f7860f
-F src/test_malloc.c cd90645ea37a5199b4cb3168223f73a29160cca9
+F src/test_malloc.c daacb05668cc10e43c71291afc23088ff372488e
 F src/test_md5.c 28209a4e2068711b5443c33104fe41f21d160071
 F src/test_mutex.c d3422d9f60cc1330249d102e74b333f0d24a0cb6
 F src/test_onefile.c 243157b10275251c5dc2d6619aee2ff9ae22379c
@@ -177,7 +177,7 @@ F src/test_schema.c 4b4bf7bb329326458c491b0e6facd4c8c4c5b479
 F src/test_server.c f0a403b5f699c09bd2b1236b6f69830fd6221f6b
 F src/test_tclvar.c 73530070df8378571c8ce6bbbbb993236ae3ad0b
 F src/test_thread.c e297dd41db0b249646e69f97d36ec13e56e8b730
-F src/tokenize.c b5fdc79fb7e00077b9c02af7a0da3b89c9f3398e
+F src/tokenize.c 70c6b5c394761816522611e70098e8c9bd58b486
 F src/trigger.c bdb56bb9db1a7b18f8505484051221ab5123f21d
 F src/update.c 4e698fcc0c91c241a960304c4236dc3a49603155
 F src/utf.c 8d52f620a7153d90b058502124fe51d821fcdf57
@@ -492,7 +492,7 @@ F test/tableapi.test a669ae9dd3bc8e7a6f74eff003664801667cf4c2
 F test/tclsqlite.test aa1781808502271feccfd24f9e2c0d2c1d7c496a
 F test/tempdb.test b88ac8a19823cf771d742bf61eef93ef337c06b1
 F test/temptable.test 19b851b9e3e64d91e9867619b2a3f5fffee6e125
-F test/tester.tcl de507ef0412c8dd9a82cd853964caffa71acbc01
+F test/tester.tcl 160c759e7e0661eaf1b4c15395ca7c0614b03d55
 F test/thread001.test 3fb08080e1fe84d1bb7ec7bbc9e13743a77e5bc5
 F test/thread002.test ed9b800460df01e3cf9428ee11dc4e3f04b9b896
 F test/thread1.test 776c9e459b75ba905193b351926ac4019b049f35
@@ -591,7 +591,7 @@ F test/zeroblob.test 792124852ec61458a2eb527b5091791215e0be95
 F tool/diffdb.c 7524b1b5df217c20cd0431f6789851a4e0cb191b
 F tool/fragck.tcl 5265a95126abcf6ab357f7efa544787e5963f439
 F tool/lemon.c 13e9c37ab9e0cc182cc10b93ac0e5270bbf472c8
-F tool/lempar.c 82ad5e30f2da013a13dc934e582b85916d456b50
+F tool/lempar.c 49e9b3b9b48f6b0799560ed4d090627c51513344
 F tool/memleak.awk 4e7690a51bf3ed757e611273d43fe3f65b510133
 F tool/memleak2.awk 9cc20c8e8f3c675efac71ea0721ee6874a1566e8
 F tool/memleak3.tcl 7707006ee908cffff210c98158788d85bb3fcdbf
@@ -612,7 +612,7 @@ F tool/speedtest16.c c8a9c793df96db7e4933f0852abb7a03d48f2e81
 F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff
 F tool/speedtest8.c 1dbced29de5f59ba2ebf877edcadf171540374d1
 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e
-P f7720f1bfcc6dcdd60002520e10f545a6f0eb126
-R f4c184b43a54e2c7baf24a4cb6e66abc
+P 22177dac2e3cd9acafe7fcc71674a675fdd098ff
+R 11e1cd41a325e7c59adaae6fe6ca47fe
 U drh
-Z 04067ce483452cdd62495d6b8ce2ca4a
+Z 73c60297f94ac2927669701b9ab7fab2
index 7d8dda27a92f5494f524b07797ce40d02082da02..f76d873620209850f979bebdd07c705e792752a7 100644 (file)
@@ -1 +1 @@
-22177dac2e3cd9acafe7fcc71674a675fdd098ff
\ No newline at end of file
+ef0250f3dc769a4acd534f31fa06d90922d4145b
\ No newline at end of file
index 246ba6ea833edc0fd74be2964f0688b88a693854..5639cbf8ab83d9c394d5d4926b1fe4bc029807ac 100644 (file)
@@ -30,7 +30,7 @@
 ** the version number) and changes its name to "sqlite3.h" as
 ** part of the build process.
 **
-** @(#) $Id: sqlite.h.in,v 1.379 2008/07/25 08:49:00 danielk1977 Exp $
+** @(#) $Id: sqlite.h.in,v 1.380 2008/07/25 15:39:04 drh Exp $
 */
 #ifndef _SQLITE3_H_
 #define _SQLITE3_H_
@@ -6119,6 +6119,10 @@ int sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetFlag);
 ** internal equivalents).  The value of interest is return in the
 ** *pHighwater parameter to [sqlite3_status()].  The value written
 ** into the *pCurrent parameter is undefined.</dd>
+**
+** <dt>SQLITE_STATUS_PARSER_STACK</dt>
+** <dd>This parameter records the deepest parser stack.  It is only
+** meaningful if SQLite is compiled with YYTRACKMAXSTACKDEPTH.</dd>
 ** </dl>
 **
 ** New status parameters may be added from time to time.
@@ -6129,6 +6133,7 @@ int sqlite3_status(int op, int *pCurrent, int *pHighwater, int resetFlag);
 #define SQLITE_STATUS_SCRATCH_USED         3
 #define SQLITE_STATUS_SCRATCH_OVERFLOW     4
 #define SQLITE_STATUS_MALLOC_SIZE          5
+#define SQLITE_STATUS_PARSER_STACK         6
 
 
 /*
index 45cbdfdb66d4e77cbd8d64cf2d4f7e8f3732a146..567239490008ebca2264e43e092d085c71965399 100644 (file)
@@ -11,7 +11,7 @@
 *************************************************************************
 ** Internal interface definitions for SQLite.
 **
-** @(#) $Id: sqliteInt.h,v 1.745 2008/07/25 08:49:00 danielk1977 Exp $
+** @(#) $Id: sqliteInt.h,v 1.746 2008/07/25 15:39:04 drh Exp $
 */
 #ifndef _SQLITEINT_H_
 #define _SQLITEINT_H_
@@ -1790,6 +1790,7 @@ struct Sqlite3Config {
   int isMallocInit;                 /* True after malloc is initialized */
   sqlite3_mutex *pInitMutex;        /* Mutex used by sqlite3_initialize() */
   int nSmall;                       /* alloc size threshold used by mem6.c */
+  int mxParserStack;                /* maximum depth of the parser stack */
 };
 
 /*
@@ -2195,6 +2196,9 @@ void sqlite3SelectDestInit(SelectDest*,int,int);
 void *sqlite3ParserAlloc(void*(*)(size_t));
 void sqlite3ParserFree(void*, void(*)(void*));
 void sqlite3Parser(void*, int, Token, Parse*);
+#ifdef YYTRACKMAXSTACKDEPTH
+  int sqlite3ParserStackPeak(void*);
+#endif
 
 int sqlite3AutoLoadExtensions(sqlite3*);
 #ifndef SQLITE_OMIT_LOAD_EXTENSION
index 5d7d6faa4ad95b80f7c0d6ce3697ca7bf9dbcf9d..504f44e50e6fe48579d4a590068943e56610013d 100644 (file)
@@ -13,7 +13,7 @@
 ** This module implements the sqlite3_status() interface and related
 ** functionality.
 **
-** $Id: status.c,v 1.3 2008/07/11 16:15:18 drh Exp $
+** $Id: status.c,v 1.4 2008/07/25 15:39:04 drh Exp $
 */
 #include "sqliteInt.h"
 
@@ -21,8 +21,8 @@
 ** Variables in which to record status information.
 */
 static struct {
-  int nowValue[6];         /* Current value */
-  int mxValue[6];          /* Maximum value */
+  int nowValue[7];         /* Current value */
+  int mxValue[7];          /* Maximum value */
 } sqlite3Stat;
 
 
index b62f8c01b02efe42fd7775003a9381cd56064bf2..b3007aa3f16cf67abffdb7896cf61d5ea9d9fb47 100644 (file)
@@ -16,7 +16,7 @@
 ** The focus of this file is providing the TCL testing layer
 ** access to compile-time constants.
 **
-** $Id: test_config.c,v 1.31 2008/07/08 23:40:20 drh Exp $
+** $Id: test_config.c,v 1.32 2008/07/25 15:39:04 drh Exp $
 */
 
 #include "sqliteLimit.h"
@@ -437,6 +437,12 @@ Tcl_SetVar2(interp, "sqlite_options", "long_double",
   Tcl_SetVar2(interp, "sqlite_options", "secure_delete", "0", TCL_GLOBAL_ONLY);
 #endif
 
+#ifdef YYTRACKMAXSTACKDEPTH
+  Tcl_SetVar2(interp, "sqlite_options", "yytrackmaxstackdepth", "1", TCL_GLOBAL_ONLY);
+#else
+  Tcl_SetVar2(interp, "sqlite_options", "yytrackmaxstackdepth", "0", TCL_GLOBAL_ONLY);
+#endif
+
 #define LINKVAR(x) { \
     static const int cv_ ## x = SQLITE_ ## x; \
     Tcl_LinkVar(interp, "SQLITE_" #x, (char *)&(cv_ ## x), \
index ea5c2d6c7377e3046e0b9c28d97158403b651a9c..0c963ad4000665d7b01954953d40fdd7b2a8a404 100644 (file)
@@ -13,7 +13,7 @@
 ** This file contains code used to implement test interfaces to the
 ** memory allocation subsystem.
 **
-** $Id: test_malloc.c,v 1.40 2008/07/25 08:49:00 danielk1977 Exp $
+** $Id: test_malloc.c,v 1.41 2008/07/25 15:39:04 drh Exp $
 */
 #include "sqliteInt.h"
 #include "tcl.h"
@@ -1083,6 +1083,7 @@ static int test_status(
     { "SQLITE_STATUS_SCRATCH_USED",        SQLITE_STATUS_SCRATCH_USED        },
     { "SQLITE_STATUS_SCRATCH_OVERFLOW",    SQLITE_STATUS_SCRATCH_OVERFLOW    },
     { "SQLITE_STATUS_MALLOC_SIZE",         SQLITE_STATUS_MALLOC_SIZE         },
+    { "SQLITE_STATUS_PARSER_STACK",        SQLITE_STATUS_PARSER_STACK        },
   };
   Tcl_Obj *pResult;
   if( objc!=3 ){
index c7769f97f73e6840654ed4bf8710e2eb3bcf0b8d..70b2d3ad9fae6cf6446b283690dd28278e7c5c30 100644 (file)
@@ -15,7 +15,7 @@
 ** individual tokens and sends those tokens one-by-one over to the
 ** parser for analysis.
 **
-** $Id: tokenize.c,v 1.146 2008/07/08 19:34:07 drh Exp $
+** $Id: tokenize.c,v 1.147 2008/07/25 15:39:04 drh Exp $
 */
 #include "sqliteInt.h"
 #include <ctype.h>
@@ -455,6 +455,11 @@ abort_parse:
     }
     sqlite3Parser(pEngine, 0, pParse->sLastToken, pParse);
   }
+#ifdef YYTRACKMAXSTACKDEPTH
+  sqlite3StatusSet(SQLITE_STATUS_PARSER_STACK,
+      sqlite3ParserStackPeak(pEngine)
+  );
+#endif /* YYDEBUG */
   sqlite3ParserFree(pEngine, sqlite3_free);
   if( db->mallocFailed ){
     pParse->rc = SQLITE_NOMEM;
index 3b4c1c136bcc495b5175eab0ae1f020202f544e0..4366dc8e0521e87974e5b70373f534b8cd0304db 100644 (file)
@@ -11,7 +11,7 @@
 # This file implements some common TCL routines used for regression
 # testing the SQLite library
 #
-# $Id: tester.tcl,v 1.132 2008/07/12 15:55:55 danielk1977 Exp $
+# $Id: tester.tcl,v 1.133 2008/07/25 15:39:04 drh Exp $
 
 #
 # What for user input before continuing.  This gives an opportunity
@@ -382,6 +382,11 @@ proc show_memstats {} {
   set x [sqlite3_status SQLITE_STATUS_SCRATCH_OVERFLOW 0]
   set val [format {now %10d  max %10d} [lindex $x 1] [lindex $x 2]]
   puts "Scratch overflow:     $val"
+  ifcapable yytrackmaxstackdepth {
+    set x [sqlite3_status SQLITE_STATUS_PARSER_STACK 0]
+    set val [format {               max %10d} [lindex $x 2]]
+    puts "Parser stack depth:    $val"
+  }
   set x [sqlite3_status SQLITE_STATUS_MALLOC_SIZE 0]
   puts "Maximum alloc size:   [lindex $x 2]"
 }
index c10f3d5fb4854e2ea8115e15b0b9d3f0a08344c5..061331f6780d0fb13266bfebcd7057adedbd092e 100644 (file)
@@ -155,6 +155,9 @@ typedef struct yyStackEntry yyStackEntry;
 ** the following structure */
 struct yyParser {
   int yyidx;                    /* Index of top element in stack */
+#ifdef YYTRACKMAXSTACKDEPTH
+  int yyidxMax;                 /* Maximum value of yyidx */
+#endif
   int yyerrcnt;                 /* Shifts left before out of the error */
   ParseARG_SDECL                /* A place to hold %extra_argument */
 #if YYSTACKDEPTH<=0
@@ -255,6 +258,9 @@ void *ParseAlloc(void *(*mallocProc)(size_t)){
   pParser = (yyParser*)(*mallocProc)( (size_t)sizeof(yyParser) );
   if( pParser ){
     pParser->yyidx = -1;
+#ifdef YYTRACKMAXSTACKDEPTH
+    pParser->yyidxMax = 0;
+#endif
 #if YYSTACKDEPTH<=0
     yyGrowStack(pParser);
 #endif
@@ -335,6 +341,16 @@ void ParseFree(
   (*freeProc)((void*)pParser);
 }
 
+/*
+** Return the peak depth of the stack for a parser.
+*/
+#ifdef YYTRACKMAXSTACKDEPTH
+int ParseStackPeak(void *p){
+  yyParser *pParser = (yyParser*)p;
+  return pParser->yyidxMax;
+}
+#endif
+
 /*
 ** Find the appropriate action for a parser given the terminal
 ** look-ahead token iLookAhead.
@@ -455,6 +471,11 @@ static void yy_shift(
 ){
   yyStackEntry *yytos;
   yypParser->yyidx++;
+#ifdef YYTRACKMAXSTACKDEPTH
+  if( yypParser->yyidx>yypParser->yyidxMax ){
+    yypParser->yyidxMax = yypParser->yyidx;
+  }
+#endif
 #if YYSTACKDEPTH>0 
   if( yypParser->yyidx>=YYSTACKDEPTH ){
     yyStackOverflow(yypParser, yypMinor);