SQLite

Check-in [7324c7f2f8]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Add tail recursion to the sqlite3ExprDelete() routine in order to keep down stack space usage for really, really large expressions. Later: The tail recursion is dangerous since the recursion might happen after the expression has been freed.
Downloads: Tarball | ZIP archive
Timelines: family | ancestors | descendants | both | mistake
Files: files | file ages | folders
SHA1: 7324c7f2f87af63729dfef2c9884c77ef9fa9d5d
User & Date: drh 2010-10-27 19:23:13.000
Original Comment: Add tail recursion to the sqlite3ExprDelete() routine in order to keep down stack space usage for really, really large expressions.
Context
2010-10-28
15:49
This was suppose to go on "trunk" but got committed to the wrong branch. Add new "dynamic_triggers" test case to threadtest3.c. (Closed-Leaf check-in: d9e588ef17 user: dan tags: mistake)
2010-10-27
19:23
Add tail recursion to the sqlite3ExprDelete() routine in order to keep down stack space usage for really, really large expressions. Later: The tail recursion is dangerous since the recursion might happen after the expression has been freed. (check-in: 7324c7f2f8 user: drh tags: mistake)
19:08
Avoid trying to allocate a negative number of bytes of memory in the test wrapper for sqlite3_blob_read(). (check-in: 739b5d9aa4 user: dan tags: trunk)
Changes
Unified Diff Ignore Whitespace Patch
Changes to src/expr.c.
606
607
608
609
610
611
612
613

614
615
616
617


618
619
620
621
622
623
624
625
626
627


628
629
630
631
632
633
634
  }
}

/*
** Recursively delete an expression tree.
*/
void sqlite3ExprDelete(sqlite3 *db, Expr *p){
  if( p==0 ) return;

  if( !ExprHasAnyProperty(p, EP_TokenOnly) ){
    sqlite3ExprDelete(db, p->pLeft);
    sqlite3ExprDelete(db, p->pRight);
    if( !ExprHasProperty(p, EP_Reduced) && (p->flags2 & EP2_MallocedToken)!=0 ){


      sqlite3DbFree(db, p->u.zToken);
    }
    if( ExprHasProperty(p, EP_xIsSelect) ){
      sqlite3SelectDelete(db, p->x.pSelect);
    }else{
      sqlite3ExprListDelete(db, p->x.pList);
    }
  }
  if( !ExprHasProperty(p, EP_Static) ){
    sqlite3DbFree(db, p);


  }
}

/*
** Return the number of bytes allocated for the expression structure 
** passed as the first argument. This is always one of EXPR_FULLSIZE,
** EXPR_REDUCEDSIZE or EXPR_TOKENONLYSIZE.







|
>
|
|
|
|
>
>
|
|
|
|
|
|
|
|
|
|
>
>







606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
  }
}

/*
** Recursively delete an expression tree.
*/
void sqlite3ExprDelete(sqlite3 *db, Expr *p){
  while( p ){
    Expr *pNext = 0;
    if( !ExprHasAnyProperty(p, EP_TokenOnly) ){
      pNext = p->pLeft;
      sqlite3ExprDelete(db, p->pRight);
      if( !ExprHasProperty(p, EP_Reduced)
       && (p->flags2 & EP2_MallocedToken)!=0
      ){
        sqlite3DbFree(db, p->u.zToken);
      }
      if( ExprHasProperty(p, EP_xIsSelect) ){
        sqlite3SelectDelete(db, p->x.pSelect);
      }else{
        sqlite3ExprListDelete(db, p->x.pList);
      }
    }
    if( !ExprHasProperty(p, EP_Static) ){
      sqlite3DbFree(db, p);
    }
    p = pNext;
  }
}

/*
** Return the number of bytes allocated for the expression structure 
** passed as the first argument. This is always one of EXPR_FULLSIZE,
** EXPR_REDUCEDSIZE or EXPR_TOKENONLYSIZE.