aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/build.c10
-rw-r--r--src/callback.c6
-rw-r--r--src/date.c5
-rw-r--r--src/main.c8
-rw-r--r--src/malloc.c4
-rw-r--r--src/select.c3
-rw-r--r--src/sqliteInt.h3
-rw-r--r--src/test1.c16
-rw-r--r--src/util.c126
9 files changed, 102 insertions, 79 deletions
diff --git a/src/build.c b/src/build.c
index 9dc63a440..065ef5305 100644
--- a/src/build.c
+++ b/src/build.c
@@ -22,7 +22,7 @@
** COMMIT
** ROLLBACK
**
-** $Id: build.c,v 1.534 2009/05/02 13:29:38 drh Exp $
+** $Id: build.c,v 1.535 2009/05/03 20:23:53 drh Exp $
*/
#include "sqliteInt.h"
@@ -261,7 +261,7 @@ Table *sqlite3FindTable(sqlite3 *db, const char *zName, const char *zDatabase){
int i;
int nName;
assert( zName!=0 );
- nName = sqlite3Strlen(db, zName);
+ nName = sqlite3Strlen30(zName);
for(i=OMIT_TEMPDB; i<db->nDb; i++){
int j = (i<2) ? i^1 : i; /* Search TEMP before MAIN */
if( zDatabase!=0 && sqlite3StrICmp(zDatabase, db->aDb[j].zName) ) continue;
@@ -323,7 +323,7 @@ Table *sqlite3LocateTable(
Index *sqlite3FindIndex(sqlite3 *db, const char *zName, const char *zDb){
Index *p = 0;
int i;
- int nName = sqlite3Strlen(db, zName);
+ int nName = sqlite3Strlen30(zName);
for(i=OMIT_TEMPDB; i<db->nDb; i++){
int j = (i<2) ? i^1 : i; /* Search TEMP before MAIN */
Schema *pSchema = db->aDb[j].pSchema;
@@ -375,7 +375,7 @@ void sqlite3UnlinkAndDeleteIndex(sqlite3 *db, int iDb, const char *zIdxName){
int len;
Hash *pHash = &db->aDb[iDb].pSchema->idxHash;
- len = sqlite3Strlen(db, zIdxName);
+ len = sqlite3Strlen30(zIdxName);
pIndex = sqlite3HashInsert(pHash, zIdxName, len, 0);
if( pIndex ){
if( pIndex->pTable->pIndex==pIndex ){
@@ -1261,7 +1261,7 @@ CollSeq *sqlite3LocateCollSeq(Parse *pParse, const char *zName, int nName){
pColl = sqlite3GetCollSeq(db, pColl, zName, nName);
if( !pColl ){
if( nName<0 ){
- nName = sqlite3Strlen(db, zName);
+ nName = sqlite3Strlen30(zName);
}
sqlite3ErrorMsg(pParse, "no such collation sequence: %.*s", nName, zName);
pColl = 0;
diff --git a/src/callback.c b/src/callback.c
index a95969b1b..2c81c9522 100644
--- a/src/callback.c
+++ b/src/callback.c
@@ -13,7 +13,7 @@
** This file contains functions used to access the internal hash tables
** of user defined functions and collation sequences.
**
-** $Id: callback.c,v 1.38 2009/05/02 13:29:38 drh Exp $
+** $Id: callback.c,v 1.39 2009/05/03 20:23:53 drh Exp $
*/
#include "sqliteInt.h"
@@ -25,7 +25,7 @@
*/
static void callCollNeeded(sqlite3 *db, const char *zName, int nName){
assert( !db->xCollNeeded || !db->xCollNeeded16 );
- if( nName<0 ) nName = sqlite3Strlen(db, zName);
+ if( nName<0 ) nName = sqlite3Strlen30(zName);
if( db->xCollNeeded ){
char *zExternal = sqlite3DbStrNDup(db, zName, nName);
if( !zExternal ) return;
@@ -158,7 +158,7 @@ static CollSeq *findCollSeqEntry(
int create
){
CollSeq *pColl;
- if( nName<0 ) nName = sqlite3Strlen(db, zName);
+ if( nName<0 ) nName = sqlite3Strlen30(zName);
pColl = sqlite3HashFind(&db->aCollSeq, zName, nName);
if( 0==pColl && create ){
diff --git a/src/date.c b/src/date.c
index a1768040f..bcd0ea86d 100644
--- a/src/date.c
+++ b/src/date.c
@@ -16,7 +16,7 @@
** sqlite3RegisterDateTimeFunctions() found at the bottom of the file.
** All other code has file scope.
**
-** $Id: date.c,v 1.106 2009/04/16 12:58:03 drh Exp $
+** $Id: date.c,v 1.107 2009/05/03 20:23:53 drh Exp $
**
** SQLite processes all times and dates as Julian Day numbers. The
** dates and times are stored as the number of days since noon
@@ -344,6 +344,7 @@ static int parseDateOrTime(
const char *zDate,
DateTime *p
){
+ int isRealNum; /* Return from sqlite3IsNumber(). Not used */
if( parseYyyyMmDd(zDate,p)==0 ){
return 0;
}else if( parseHhMmSs(zDate, p)==0 ){
@@ -351,7 +352,7 @@ static int parseDateOrTime(
}else if( sqlite3StrICmp(zDate,"now")==0){
setDateTimeToCurrent(context, p);
return 0;
- }else if( sqlite3IsNumber(zDate, 0, SQLITE_UTF8) ){
+ }else if( sqlite3IsNumber(zDate, &isRealNum, SQLITE_UTF8) ){
double r;
getValue(zDate, &r);
p->iJD = (sqlite3_int64)(r*86400000.0 + 0.5);
diff --git a/src/main.c b/src/main.c
index cc2a81057..7a1984173 100644
--- a/src/main.c
+++ b/src/main.c
@@ -14,7 +14,7 @@
** other files are for internal use by SQLite and should not be
** accessed by users of the library.
**
-** $Id: main.c,v 1.545 2009/05/02 13:29:38 drh Exp $
+** $Id: main.c,v 1.546 2009/05/03 20:23:53 drh Exp $
*/
#include "sqliteInt.h"
@@ -930,7 +930,7 @@ int sqlite3CreateFunc(
(!xFunc && (xFinal && !xStep)) ||
(!xFunc && (!xFinal && xStep)) ||
(nArg<-1 || nArg>SQLITE_MAX_FUNCTION_ARG) ||
- (255<(nName = sqlite3Strlen(db, zFunctionName))) ){
+ (255<(nName = sqlite3Strlen30( zFunctionName))) ){
sqlite3Error(db, SQLITE_ERROR, "bad parameters");
return SQLITE_ERROR;
}
@@ -1056,7 +1056,7 @@ int sqlite3_overload_function(
const char *zName,
int nArg
){
- int nName = sqlite3Strlen(db, zName);
+ int nName = sqlite3Strlen30(zName);
int rc;
sqlite3_mutex_enter(db->mutex);
if( sqlite3FindFunction(db, zName, nName, nArg, SQLITE_UTF8, 0)==0 ){
@@ -1383,7 +1383,7 @@ static int createCollation(
** sequence. If so, and there are active VMs, return busy. If there
** are no active VMs, invalidate any pre-compiled statements.
*/
- nName = sqlite3Strlen(db, zName);
+ nName = sqlite3Strlen30(zName);
pColl = sqlite3FindCollSeq(db, (u8)enc2, zName, nName, 0);
if( pColl && pColl->xCmp ){
if( db->activeVdbeCnt ){
diff --git a/src/malloc.c b/src/malloc.c
index 92e56394e..70d691601 100644
--- a/src/malloc.c
+++ b/src/malloc.c
@@ -12,7 +12,7 @@
**
** Memory allocation functions used throughout sqlite.
**
-** $Id: malloc.c,v 1.61 2009/03/24 15:08:10 drh Exp $
+** $Id: malloc.c,v 1.62 2009/05/03 20:23:54 drh Exp $
*/
#include "sqliteInt.h"
#include <stdarg.h>
@@ -651,7 +651,7 @@ char *sqlite3DbStrDup(sqlite3 *db, const char *z){
if( z==0 ){
return 0;
}
- n = (db ? sqlite3Strlen(db, z) : sqlite3Strlen30(z))+1;
+ n = sqlite3Strlen30(z) + 1;
assert( (n&0x7fffffff)==n );
zNew = sqlite3DbMallocRaw(db, (int)n);
if( zNew ){
diff --git a/src/select.c b/src/select.c
index 54600e53d..d1c0fb44e 100644
--- a/src/select.c
+++ b/src/select.c
@@ -12,7 +12,7 @@
** This file contains C code routines that are called by the parser
** to handle SELECT statements in SQLite.
**
-** $Id: select.c,v 1.511 2009/05/01 21:13:37 drh Exp $
+** $Id: select.c,v 1.512 2009/05/03 20:23:54 drh Exp $
*/
#include "sqliteInt.h"
@@ -1157,7 +1157,6 @@ static int selectColumnsFromExprList(
sqlite3DbFree(db, zName);
break;
}
- sqlite3Dequote(zName);
/* Make sure the column name is unique. If the name is not unique,
** append a integer to the name so that it becomes unique.
diff --git a/src/sqliteInt.h b/src/sqliteInt.h
index 52093c092..c5282b340 100644
--- a/src/sqliteInt.h
+++ b/src/sqliteInt.h
@@ -11,7 +11,7 @@
*************************************************************************
** Internal interface definitions for SQLite.
**
-** @(#) $Id: sqliteInt.h,v 1.866 2009/05/02 13:29:38 drh Exp $
+** @(#) $Id: sqliteInt.h,v 1.867 2009/05/03 20:23:54 drh Exp $
*/
#ifndef _SQLITEINT_H_
#define _SQLITEINT_H_
@@ -2294,7 +2294,6 @@ int sqlite3WalkSelectFrom(Walker*, Select*);
int sqlite3StrICmp(const char *, const char *);
int sqlite3StrNICmp(const char *, const char *, int);
int sqlite3IsNumber(const char*, int*, u8);
-int sqlite3Strlen(sqlite3*, const char*);
int sqlite3Strlen30(const char*);
int sqlite3MallocInit(void);
diff --git a/src/test1.c b/src/test1.c
index 384166e06..72eeb1ae9 100644
--- a/src/test1.c
+++ b/src/test1.c
@@ -13,7 +13,7 @@
** is not included in the SQLite library. It is used for automated
** testing of the SQLite library.
**
-** $Id: test1.c,v 1.352 2009/04/28 15:35:39 danielk1977 Exp $
+** $Id: test1.c,v 1.353 2009/05/03 20:23:54 drh Exp $
*/
#include "sqliteInt.h"
#include "tcl.h"
@@ -1218,18 +1218,6 @@ static int sqlite3_mprintf_int(
}
/*
-** If zNum represents an integer that will fit in 64-bits, then set
-** *pValue to that integer and return true. Otherwise return false.
-*/
-static int sqlite3GetInt64(const char *zNum, i64 *pValue){
- if( sqlite3FitsIn64Bits(zNum, 0) ){
- sqlite3Atoi64(zNum, pValue);
- return 1;
- }
- return 0;
-}
-
-/*
** Usage: sqlite3_mprintf_int64 FORMAT INTEGER INTEGER INTEGER
**
** Call mprintf with three 64-bit integer arguments
@@ -1249,7 +1237,7 @@ static int sqlite3_mprintf_int64(
return TCL_ERROR;
}
for(i=2; i<5; i++){
- if( !sqlite3GetInt64(argv[i], &a[i-2]) ){
+ if( !sqlite3Atoi64(argv[i], &a[i-2]) ){
Tcl_AppendResult(interp, "argument is not a valid 64-bit integer", 0);
return TCL_ERROR;
}
diff --git a/src/util.c b/src/util.c
index b2ab11101..b9d545f46 100644
--- a/src/util.c
+++ b/src/util.c
@@ -14,7 +14,7 @@
** This file contains functions for allocating memory, comparing
** strings, and stuff like that.
**
-** $Id: util.c,v 1.252 2009/05/01 21:13:37 drh Exp $
+** $Id: util.c,v 1.253 2009/05/03 20:23:54 drh Exp $
*/
#include "sqliteInt.h"
#include <stdarg.h>
@@ -58,6 +58,7 @@ int sqlite3Assert(void){
** Otherwise, we have our own implementation that works on most systems.
*/
int sqlite3IsNaN(double x){
+ int rc; /* The value return */
#if !defined(SQLITE_HAVE_ISNAN)
/*
** Systems that support the isnan() library function should probably
@@ -87,15 +88,21 @@ int sqlite3IsNaN(double x){
#endif
volatile double y = x;
volatile double z = y;
- return y!=z;
+ rc = (y!=z);
#else /* if defined(SQLITE_HAVE_ISNAN) */
- return isnan(x);
+ rc = isnan(x);
#endif /* SQLITE_HAVE_ISNAN */
+ testcase( rc );
+ return rc;
}
/*
** Compute a string length that is limited to what can be stored in
** lower 30 bits of a 32-bit signed integer.
+**
+** The value returned will never be negative. Nor will it ever be greater
+** than the actual length of the string. For very long strings (greater
+** than 1GiB) the value returned might be less than the true string length.
*/
int sqlite3Strlen30(const char *z){
const char *z2 = z;
@@ -104,24 +111,6 @@ int sqlite3Strlen30(const char *z){
}
/*
-** Return the length of a string, except do not allow the string length
-** to exceed the SQLITE_LIMIT_LENGTH setting.
-*/
-int sqlite3Strlen(sqlite3 *db, const char *z){
- const char *z2 = z;
- int len;
- int x;
- while( *z2 ){ z2++; }
- x = (int)(z2 - z);
- len = 0x7fffffff & x;
- if( len!=x || len > db->aLimit[SQLITE_LIMIT_LENGTH] ){
- return db->aLimit[SQLITE_LIMIT_LENGTH];
- }else{
- return len;
- }
-}
-
-/*
** Set the most recent error code and error string for the sqlite
** handle "db". The error code is set to "err_code".
**
@@ -179,6 +168,7 @@ void sqlite3ErrorMsg(Parse *pParse, const char *zFormat, ...){
va_list ap;
sqlite3 *db = pParse->db;
pParse->nErr++;
+ testcase( pParse->zErrMsg!=0 );
sqlite3DbFree(db, pParse->zErrMsg);
va_start(ap, zFormat);
pParse->zErrMsg = sqlite3VMPrintf(db, zFormat, ap);
@@ -226,7 +216,7 @@ int sqlite3Dequote(char *z){
case '[': quote = ']'; break; /* For MS SqlServer compatibility */
default: return -1;
}
- for(i=1, j=0; z[i]; i++){
+ for(i=1, j=0; ALWAYS(z[i]); i++){
if( z[i]==quote ){
if( z[i+1]==quote ){
z[j++] = quote;
@@ -265,10 +255,15 @@ int sqlite3StrNICmp(const char *zLeft, const char *zRight, int N){
}
/*
-** Return TRUE if z is a pure numeric string. Return FALSE if the
-** string contains any character which is not part of a number. If
-** the string is numeric and contains the '.' character, set *realnum
-** to TRUE (otherwise FALSE).
+** Return TRUE if z is a pure numeric string. Return FALSE and leave
+** *realnum unchanged if the string contains any character which is not
+** part of a number.
+**
+** If the string is pure numeric, set *realnum to TRUE if the string
+** contains the '.' character or an "E+000" style exponentiation suffix.
+** Otherwise set *realnum to FALSE. Note that just becaue *realnum is
+** false does not mean that the number can be successfully converted into
+** an integer - it might be too big.
**
** An empty string is considered non-numeric.
*/
@@ -280,20 +275,20 @@ int sqlite3IsNumber(const char *z, int *realnum, u8 enc){
return 0;
}
z += incr;
- if( realnum ) *realnum = 0;
+ *realnum = 0;
while( sqlite3Isdigit(*z) ){ z += incr; }
if( *z=='.' ){
z += incr;
if( !sqlite3Isdigit(*z) ) return 0;
while( sqlite3Isdigit(*z) ){ z += incr; }
- if( realnum ) *realnum = 1;
+ *realnum = 1;
}
if( *z=='e' || *z=='E' ){
z += incr;
if( *z=='+' || *z=='-' ) z += incr;
if( !sqlite3Isdigit(*z) ) return 0;
while( sqlite3Isdigit(*z) ){ z += incr; }
- if( realnum ) *realnum = 1;
+ *realnum = 1;
}
return *z==0;
}
@@ -452,25 +447,25 @@ int sqlite3Atoi64(const char *zNum, i64 *pNum){
}
/*
-** The string zNum represents an integer. There might be some other
+** The string zNum represents an unsigned integer. There might be some other
** information following the integer too, but that part is ignored.
** If the integer that the prefix of zNum represents will fit in a
** 64-bit signed integer, return TRUE. Otherwise return FALSE.
**
-** This routine returns FALSE for the string -9223372036854775808 even that
-** that number will, in theory fit in a 64-bit integer. Positive
-** 9223373036854775808 will not fit in 64 bits. So it seems safer to return
-** false.
+** If the negFlag parameter is true, that means that zNum really represents
+** a negative number. (The leading "-" is omitted from zNum.) This
+** parameter is needed to determine a boundary case. A string
+** of "9223373036854775808" returns false if negFlag is false or true
+** if negFlag is true.
+**
+** Leading zeros are ignored.
*/
int sqlite3FitsIn64Bits(const char *zNum, int negFlag){
int i, c;
int neg = 0;
- if( *zNum=='-' ){
- neg = 1;
- zNum++;
- }else if( *zNum=='+' ){
- zNum++;
- }
+
+ assert( zNum[0]>='0' && zNum[0]<='9' ); /* zNum is an unsigned number */
+
if( negFlag ) neg = 1-neg;
while( *zNum=='0' ){
zNum++; /* Skip leading zeros. Ticket #2454 */
@@ -775,33 +770,40 @@ u8 sqlite3GetVarint(const unsigned char *p, u64 *v){
u8 sqlite3GetVarint32(const unsigned char *p, u32 *v){
u32 a,b;
+ /* The 1-byte case. Overwhelmingly the most common. Handled inline
+ ** by the getVarin32() macro */
a = *p;
/* a: p0 (unmasked) */
#ifndef getVarint32
if (!(a&0x80))
{
+ /* Values between 0 and 127 */
*v = a;
return 1;
}
#endif
+ /* The 2-byte case */
p++;
b = *p;
/* b: p1 (unmasked) */
if (!(b&0x80))
{
+ /* Values between 128 and 16383 */
a &= 0x7f;
a = a<<7;
*v = a | b;
return 2;
}
+ /* The 3-byte case */
p++;
a = a<<14;
a |= *p;
/* a: p0<<14 | p2 (unmasked) */
if (!(a&0x80))
{
+ /* Values between 16384 and 2097151 */
a &= (0x7f<<14)|(0x7f);
b &= 0x7f;
b = b<<7;
@@ -809,12 +811,39 @@ u8 sqlite3GetVarint32(const unsigned char *p, u32 *v){
return 3;
}
+ /* A 32-bit varint is used to store size information in btrees.
+ ** Objects are rarely larger than 2MiB limit of a 3-byte varint.
+ ** A 3-byte varint is sufficient, for example, to record the size
+ ** of a 1048569-byte BLOB or string.
+ **
+ ** We only unroll the first 1-, 2-, and 3- byte cases. The very
+ ** rare larger cases can be handled by the slower 64-bit varint
+ ** routine.
+ */
+#if 1
+ {
+ u64 v64;
+ u8 n;
+
+ p -= 2;
+ n = sqlite3GetVarint(p, &v64);
+ assert( n>3 && n<=9 );
+ *v = (u32)v64;
+ return n;
+ }
+
+#else
+ /* For following code (kept for historical record only) shows an
+ ** unrolling for the 3- and 4-byte varint cases. This code is
+ ** slightly faster, but it is also larger and much harder to test.
+ */
p++;
b = b<<14;
b |= *p;
/* b: p1<<14 | p3 (unmasked) */
if (!(b&0x80))
{
+ /* Values between 2097152 and 268435455 */
b &= (0x7f<<14)|(0x7f);
a &= (0x7f<<14)|(0x7f);
a = a<<7;
@@ -828,6 +857,7 @@ u8 sqlite3GetVarint32(const unsigned char *p, u32 *v){
/* a: p0<<28 | p2<<14 | p4 (unmasked) */
if (!(a&0x80))
{
+ /* Walues between 268435456 and 34359738367 */
a &= (0x1f<<28)|(0x7f<<14)|(0x7f);
b &= (0x1f<<28)|(0x7f<<14)|(0x7f);
b = b<<7;
@@ -849,6 +879,7 @@ u8 sqlite3GetVarint32(const unsigned char *p, u32 *v){
*v = (u32)v64;
return n;
}
+#endif
}
/*
@@ -860,7 +891,7 @@ int sqlite3VarintLen(u64 v){
do{
i++;
v >>= 7;
- }while( v!=0 && i<9 );
+ }while( v!=0 && ALWAYS(i<9) );
return i;
}
@@ -998,13 +1029,18 @@ int sqlite3SafetyCheckOk(sqlite3 *db){
u32 magic;
if( db==0 ) return 0;
magic = db->magic;
- if( magic!=SQLITE_MAGIC_OPEN &&
- magic!=SQLITE_MAGIC_BUSY ) return 0;
- return 1;
+ if( magic!=SQLITE_MAGIC_OPEN
+#ifdef SQLITE_DEBUG
+ && magic!=SQLITE_MAGIC_BUSY
+#endif
+ ){
+ return 0;
+ }else{
+ return 1;
+ }
}
int sqlite3SafetyCheckSickOrOk(sqlite3 *db){
u32 magic;
- if( db==0 ) return 0;
magic = db->magic;
if( magic!=SQLITE_MAGIC_SICK &&
magic!=SQLITE_MAGIC_OPEN &&