/ Check-in [5963de30]
Login

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

Overview
Comment:Remove the nAlloc field from the ExprList object.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1:5963de303a9106b446a9423aa838bfdf6bc1e7f3
User & Date: drh 2012-02-02 01:58:08
Context
2012-02-02
03:11
Fix a possible segfault after an OOM fault. This has been in the code for ages but only expressed itself following the previous check-in. check-in: a3553b8a user: drh tags: trunk
01:58
Remove the nAlloc field from the ExprList object. check-in: 5963de30 user: drh tags: trunk
2012-02-01
19:03
Very small performance enhancement and reduction in size of the sqlite3_stmt object. check-in: a38d57a4 user: drh tags: trunk
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/expr.c.

   852    852     ExprList *pNew;
   853    853     struct ExprList_item *pItem, *pOldItem;
   854    854     int i;
   855    855     if( p==0 ) return 0;
   856    856     pNew = sqlite3DbMallocRaw(db, sizeof(*pNew) );
   857    857     if( pNew==0 ) return 0;
   858    858     pNew->iECursor = 0;
   859         -  pNew->nExpr = pNew->nAlloc = p->nExpr;
   860         -  pNew->a = pItem = sqlite3DbMallocRaw(db,  p->nExpr*sizeof(p->a[0]) );
          859  +  pNew->nExpr = i = p->nExpr;
          860  +  if( (flags & EXPRDUP_REDUCE)==0 ) for(i=1; i<p->nExpr; i+=i){}
          861  +  pNew->a = pItem = sqlite3DbMallocRaw(db,  i*sizeof(p->a[0]) );
   861    862     if( pItem==0 ){
   862    863       sqlite3DbFree(db, pNew);
   863    864       return 0;
   864    865     } 
   865    866     pOldItem = p->a;
   866    867     for(i=0; i<p->nExpr; i++, pItem++, pOldItem++){
   867    868       Expr *pOldExpr = pOldItem->pExpr;
................................................................................
   988    989   ){
   989    990     sqlite3 *db = pParse->db;
   990    991     if( pList==0 ){
   991    992       pList = sqlite3DbMallocZero(db, sizeof(ExprList) );
   992    993       if( pList==0 ){
   993    994         goto no_mem;
   994    995       }
   995         -    assert( pList->nAlloc==0 );
   996         -  }
   997         -  if( pList->nAlloc<=pList->nExpr ){
          996  +    pList->a = sqlite3DbMallocRaw(db, sizeof(pList->a[0]));
          997  +    if( pList->a==0 ) goto no_mem;
          998  +  }else if( (pList->nExpr & (pList->nExpr-1))==0 ){
   998    999       struct ExprList_item *a;
   999         -    int n = pList->nAlloc*2 + 4;
  1000         -    a = sqlite3DbRealloc(db, pList->a, n*sizeof(pList->a[0]));
         1000  +    assert( pList->nExpr>0 );
         1001  +    a = sqlite3DbRealloc(db, pList->a, pList->nExpr*2*sizeof(pList->a[0]));
  1001   1002       if( a==0 ){
  1002   1003         goto no_mem;
  1003   1004       }
  1004   1005       pList->a = a;
  1005         -    pList->nAlloc = sqlite3DbMallocSize(db, a)/sizeof(a[0]);
  1006   1006     }
  1007   1007     assert( pList->a!=0 );
  1008   1008     if( 1 ){
  1009   1009       struct ExprList_item *pItem = &pList->a[pList->nExpr++];
  1010   1010       memset(pItem, 0, sizeof(*pItem));
  1011   1011       pItem->pExpr = pExpr;
  1012   1012     }
................................................................................
  1089   1089   /*
  1090   1090   ** Delete an entire expression list.
  1091   1091   */
  1092   1092   void sqlite3ExprListDelete(sqlite3 *db, ExprList *pList){
  1093   1093     int i;
  1094   1094     struct ExprList_item *pItem;
  1095   1095     if( pList==0 ) return;
  1096         -  assert( pList->a!=0 || (pList->nExpr==0 && pList->nAlloc==0) );
  1097         -  assert( pList->nExpr<=pList->nAlloc );
         1096  +  assert( pList->a!=0 || pList->nExpr==0 );
  1098   1097     for(pItem=pList->a, i=0; i<pList->nExpr; i++, pItem++){
  1099   1098       sqlite3ExprDelete(db, pItem->pExpr);
  1100   1099       sqlite3DbFree(db, pItem->zName);
  1101   1100       sqlite3DbFree(db, pItem->zSpan);
  1102   1101     }
  1103   1102     sqlite3DbFree(db, pList->a);
  1104   1103     sqlite3DbFree(db, pList);

Changes to src/sqliteInt.h.

  1771   1771   ** as the list of "expr AS ID" fields following a "SELECT" or in the
  1772   1772   ** list of "ID = expr" items in an UPDATE.  A list of expressions can
  1773   1773   ** also be used as the argument to a function, in which case the a.zName
  1774   1774   ** field is not used.
  1775   1775   */
  1776   1776   struct ExprList {
  1777   1777     int nExpr;             /* Number of expressions on the list */
  1778         -  int nAlloc;            /* Number of entries allocated below */
  1779   1778     int iECursor;          /* VDBE Cursor associated with this ExprList */
  1780         -  struct ExprList_item {
         1779  +  struct ExprList_item { /* For each expression in the list */
  1781   1780       Expr *pExpr;           /* The list of expressions */
  1782   1781       char *zName;           /* Token associated with this expression */
  1783   1782       char *zSpan;           /* Original text of the expression */
  1784   1783       u8 sortOrder;          /* 1 for DESC or 0 for ASC */
  1785   1784       u8 done;               /* A flag to indicate when processing is finished */
  1786   1785       u16 iOrderByCol;       /* For ORDER BY, column number in result set */
  1787   1786       u16 iAlias;            /* Index into Parse.aAlias[] for zName */
  1788         -  } *a;                  /* One entry for each expression */
         1787  +  } *a;                  /* Alloc a power of two greater or equal to nExpr */
  1789   1788   };
  1790   1789   
  1791   1790   /*
  1792   1791   ** An instance of this structure is used by the parser to record both
  1793   1792   ** the parse tree for an expression and the span of input text for an
  1794   1793   ** expression.
  1795   1794   */