aboutsummaryrefslogtreecommitdiff
path: root/src/expr.c
diff options
context:
space:
mode:
authordanielk1977 <danielk1977@noemail.net>2005-03-16 12:15:20 +0000
committerdanielk1977 <danielk1977@noemail.net>2005-03-16 12:15:20 +0000
commitd5d565235b23ee3827515ddce486735322fc5857 (patch)
tree8ad88f3dd36acbd9edc76ad34b5292014ec34654 /src/expr.c
parent165ffe9708d95c2c81206f526cb8b1fd4ab787f1 (diff)
downloadsqlite-d5d565235b23ee3827515ddce486735322fc5857.tar.gz
sqlite-d5d565235b23ee3827515ddce486735322fc5857.zip
Fix some memory leaks that can occur if a memory allocation fails. (CVS 2388)
FossilOrigin-Name: 9a358fc33d726d0b5782bf65b50f61f2bd096d56
Diffstat (limited to 'src/expr.c')
-rw-r--r--src/expr.c43
1 files changed, 29 insertions, 14 deletions
diff --git a/src/expr.c b/src/expr.c
index 1723e60c7..6240656f9 100644
--- a/src/expr.c
+++ b/src/expr.c
@@ -12,7 +12,7 @@
** This file contains routines used for analyzing expressions and
** for generating VDBE code that evaluates expressions in SQLite.
**
-** $Id: expr.c,v 1.195 2005/03/09 12:26:51 danielk1977 Exp $
+** $Id: expr.c,v 1.196 2005/03/16 12:15:21 danielk1977 Exp $
*/
#include "sqliteInt.h"
#include <ctype.h>
@@ -183,7 +183,12 @@ Expr *sqlite3Expr(int op, Expr *pLeft, Expr *pRight, const Token *pToken){
Expr *pNew;
pNew = sqliteMalloc( sizeof(Expr) );
if( pNew==0 ){
- /* When malloc fails, we leak memory from pLeft and pRight */
+ /* When malloc fails, delete pLeft and pRight. Expressions passed to
+ ** this function must always be allocated with sqlite3Expr() for this
+ ** reason.
+ */
+ sqlite3ExprDelete(pLeft);
+ sqlite3ExprDelete(pRight);
return 0;
}
pNew->op = op;
@@ -275,7 +280,7 @@ Expr *sqlite3ExprFunction(ExprList *pList, Token *pToken){
Expr *pNew;
pNew = sqliteMalloc( sizeof(Expr) );
if( pNew==0 ){
- /* sqlite3ExprListDelete(pList); // Leak pList when malloc fails */
+ sqlite3ExprListDelete(pList); /* Avoid leaking memory when malloc fails */
return 0;
}
pNew->op = TK_FUNCTION;
@@ -493,7 +498,10 @@ IdList *sqlite3IdListDup(IdList *p){
if( pNew==0 ) return 0;
pNew->nId = pNew->nAlloc = p->nId;
pNew->a = sqliteMallocRaw( p->nId*sizeof(p->a[0]) );
- if( pNew->a==0 ) return 0;
+ if( pNew->a==0 ){
+ sqliteFree(pNew);
+ return 0;
+ }
for(i=0; i<p->nId; i++){
struct IdList_item *pNewItem = &pNew->a[i];
struct IdList_item *pOldItem = &p->a[i];
@@ -542,19 +550,19 @@ ExprList *sqlite3ExprListAppend(ExprList *pList, Expr *pExpr, Token *pName){
if( pList==0 ){
pList = sqliteMalloc( sizeof(ExprList) );
if( pList==0 ){
- /* sqlite3ExprDelete(pExpr); // Leak memory if malloc fails */
- return 0;
+ goto no_mem;
}
assert( pList->nAlloc==0 );
}
if( pList->nAlloc<=pList->nExpr ){
- pList->nAlloc = pList->nAlloc*2 + 4;
- pList->a = sqliteRealloc(pList->a, pList->nAlloc*sizeof(pList->a[0]));
- if( pList->a==0 ){
- /* sqlite3ExprDelete(pExpr); // Leak memory if malloc fails */
- pList->nExpr = pList->nAlloc = 0;
- return pList;
- }
+ struct ExprList_item *a;
+ int n = pList->nAlloc*2 + 4;
+ a = sqliteRealloc(pList->a, n*sizeof(pList->a[0]));
+ if( a==0 ){
+ goto no_mem;
+ }
+ pList->a = a;
+ pList->nAlloc = n;
}
assert( pList->a!=0 );
if( pExpr || pName ){
@@ -564,6 +572,12 @@ ExprList *sqlite3ExprListAppend(ExprList *pList, Expr *pExpr, Token *pName){
pItem->zName = sqlite3NameFromToken(pName);
}
return pList;
+
+no_mem:
+ /* Avoid leaking memory if malloc has failed. */
+ sqlite3ExprDelete(pExpr);
+ sqlite3ExprListDelete(pList);
+ return 0;
}
/*
@@ -769,7 +783,7 @@ static int lookupName(
zTab = sqlite3NameFromToken(pTableToken);
zCol = sqlite3NameFromToken(pColumnToken);
if( sqlite3_malloc_failed ){
- return 1; /* Leak memory (zDb and zTab) if malloc fails */
+ goto lookupname_end;
}
pExpr->iTable = -1;
@@ -947,6 +961,7 @@ static int lookupName(
pMatch->colUsed |= 1<<n;
}
+lookupname_end:
/* Clean up and return
*/
sqliteFree(zDb);