-C Report\san\serror\swhen\strying\sto\sresolve\scolumn\sname\s"rowid"\sin\sa\nWITHOUT\sROWID\stable.
-D 2013-10-23T17:39:41.217
+C Construct\ssecondary\sindices\son\sWITHOUT\sROWID\stables.
+D 2013-10-23T22:23:03.281
F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
F Makefile.in 0522b53cdc1fcfc18f3a98e0246add129136c654
F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
F src/btree.c 509722ce305471b626d3401c0631a808fd33237b
F src/btree.h bfe0e8c5759b4ec77b0d18390064a6ef3cdffaaf
F src/btreeInt.h f038e818bfadf75afbd09819ed93c26a333d39e0
-F src/build.c 029e1709651df95c75477c334be7bc1ea9332e6d
+F src/build.c 6970691b8d22c6eb2c1ab0078e4d25c939acfdad
F src/callback.c f99a8957ba2adf369645fac0db09ad8adcf1caa2
F src/complete.c dc1d136c0feee03c2f7550bafc0d29075e36deac
F src/ctime.c ea4b7f3623a0fcb1146e7f245d7410033e86859c
F src/date.c 593c744b2623971e45affd0bde347631bdfa4625
-F src/delete.c c1547dbf732c9987d109b6f45729b4a70e14659e
+F src/delete.c 5dcd957b7af5b67b4cce125dd2b580248678db8a
F src/expr.c 3180b6332072b263f845592e72e92971af562ab0
F src/fault.c 160a0c015b6c2629d3899ed2daf63d75754a32bb
F src/fkey.c 628f81177299660a86e40359b3689b81f517e125
F src/pcache.c f8043b433a57aba85384a531e3937a804432a346
F src/pcache.h a5e4f5d9f5d592051d91212c5949517971ae6222
F src/pcache1.c a467393909a4ed7ca9de066d85ba5c5b04a5be63
-F src/pragma.c ab815d27690d24e87c953355a765edb546c47708
+F src/pragma.c 575a4462366b371076dd14bd93df21f325a10995
F src/prepare.c f47ba2bba7ac5650881ab6c41f6d33a6de1a8d52
F src/printf.c da9119eb31a187a4b99f60aa4a225141c0ebb74b
F src/random.c 0b2dbc37fdfbfa6bd455b091dfcef5bdb32dba68
F src/sqlite.h.in 547a44dd4ff4d975e92a645ea2d609e543a83d0f
F src/sqlite3.rc 11094cc6a157a028b301a9f06b3d03089ea37c3e
F src/sqlite3ext.h 886f5a34de171002ad46fae8c36a7d8051c190fc
-F src/sqliteInt.h dc7c57e1d792cda4af5a21bc9566a9afe63f977f
+F src/sqliteInt.h 62dee86c51c7b2dc73b0f2cbdfa332a4b79f9bcf
F src/sqliteLimit.h 164b0e6749d31e0daa1a4589a169d31c0dec7b3d
F src/status.c 7ac05a5c7017d0b9f0b4bcd701228b784f987158
F src/table.c 2cd62736f845d82200acfa1287e33feb3c15d62e
F src/wal.c 7dc3966ef98b74422267e7e6e46e07ff6c6eb1b4
F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4
F src/walker.c e9e593d5bb798c3e67fc3893dfe7055c9e7d8d74
-F src/where.c f9e7662714d776a929683d813a2496fbca8b9087
+F src/where.c 13add0a866a75adb345abfa2ad25585322d472f3
F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2
F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2
F test/aggnested.test 45c0201e28045ad38a530b5a144b73cd4aa2cfd6
F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
F tool/warnings.sh d1a6de74685f360ab718efda6265994b99bbea01
F tool/win/sqlite.vsix 030f3eeaf2cb811a3692ab9c14d021a75ce41fff
-P 579815fff1737552d2077255862b8f4fd220927c
-R d63ce5fb7a4f24abe25c071303585c0a
+P 36bcc9cb885523fba2f3b0d152de9e08073668c1
+R 5319af9bbb603de112b9787a2a60f8ed
U drh
-Z 3ecb7889d41fd9bb93bb233d04c44ce3
+Z 289de8cc66e2b52514de0b537df4236c
-36bcc9cb885523fba2f3b0d152de9e08073668c1
\ No newline at end of file
+2c028ddc85cb45746cad6ab0cefd99134fbd50d7
\ No newline at end of file
return SQLITE_OK;
}
+/*
+** Return the PRIMARY KEY index of a table
+*/
+Index *sqlite3PrimaryKeyIndex(Table *pTab){
+ Index *p;
+ for(p=pTab->pIndex; p && p->autoIndex!=2; p=p->pNext){}
+ return p;
+}
+
+/*
+** Return the column of index pIdx that corresponds to table
+** column iCol. Return -1 if not found.
+*/
+i16 sqlite3ColumnOfIndex(Index *pIdx, i16 iCol){
+ int i;
+ for(i=0; i<pIdx->nColumn; i++){
+ if( iCol==pIdx->aiColumn[i] ) return i;
+ }
+ return -1;
+}
+
/*
** Begin constructing a new table representation in memory. This is
** the first of several action routines that get called in response
pPk = sqlite3CreateIndex(pParse, 0, 0, 0, pList, pTab->keyConf, 0, 0, 0, 0);
if( pPk==0 ) return;
pTab->iPKey = -1;
+ }else{
+ pPk = sqlite3PrimaryKeyIndex(pTab);
}
- for(pPk=pTab->pIndex; pPk && pPk->autoIndex<2; pPk=pPk->pNext){}
assert( pPk!=0 );
nPk = pPk->nKeyCol;
tnum = memRootPage;
}else{
tnum = pIndex->tnum;
- sqlite3VdbeAddOp2(v, OP_Clear, tnum, iDb);
}
pKey = sqlite3IndexKeyinfo(pParse, pIndex);
- sqlite3VdbeAddOp4(v, OP_OpenWrite, iIdx, tnum, iDb,
- (char *)pKey, P4_KEYINFO_HANDOFF);
- sqlite3VdbeChangeP5(v, OPFLAG_BULKCSR|((memRootPage>=0)?OPFLAG_P2ISREG:0));
/* Open the sorter cursor if we are to use one. */
iSorter = pParse->nTab++;
/* Open the table. Loop through all rows of the table, inserting index
** records into the sorter. */
- sqlite3OpenTable(pParse, iTab, iDb, pTab, OP_OpenRead);
+ if( HasRowid(pTab) ){
+ sqlite3OpenTable(pParse, iTab, iDb, pTab, OP_OpenRead);
+ }else{
+ Index *pPk = sqlite3PrimaryKeyIndex(pTab);
+ assert( pPk!=0 );
+ assert( pPk->tnum=pTab->tnum );
+ sqlite3VdbeAddOp4(v, OP_OpenRead, iTab, pPk->tnum, iDb,
+ (char*)sqlite3IndexKeyinfo(pParse, pPk),
+ P4_KEYINFO_HANDOFF);
+ }
addr1 = sqlite3VdbeAddOp2(v, OP_Rewind, iTab, 0);
regRecord = sqlite3GetTempReg(pParse);
sqlite3VdbeResolveLabel(v, iPartIdxLabel);
sqlite3VdbeAddOp2(v, OP_Next, iTab, addr1+1);
sqlite3VdbeJumpHere(v, addr1);
+ if( memRootPage<0 ) sqlite3VdbeAddOp2(v, OP_Clear, tnum, iDb);
+ sqlite3VdbeAddOp4(v, OP_OpenWrite, iIdx, tnum, iDb,
+ (char *)pKey, P4_KEYINFO_HANDOFF);
+ sqlite3VdbeChangeP5(v, OPFLAG_BULKCSR|((memRootPage>=0)?OPFLAG_P2ISREG:0));
+
addr1 = sqlite3VdbeAddOp2(v, OP_SorterSort, iSorter, 0);
if( pIndex->onError!=OE_None ){
int j2 = sqlite3VdbeCurrentAddr(v) + 3;
struct ExprList_item *pListItem; /* For looping over pList */
const Column *pTabCol; /* A column in the table */
int nExtra = 0; /* Space allocated for zExtra[] */
+ int nExtraCol; /* Number of extra columns needed */
char *zExtra; /* Extra space after the Index object */
+ Index *pPk = 0; /* PRIMARY KEY index for WITHOUT ROWID tables */
assert( pParse->nErr==0 ); /* Never called with prior errors */
if( db->mallocFailed || IN_DECLARE_VTAB ){
pTab->zName);
goto exit_create_index;
}
+ if( !HasRowid(pTab) ) pPk = sqlite3PrimaryKeyIndex(pTab);
}else{
assert( pName==0 );
assert( pStart==0 );
** Allocate the index structure.
*/
nName = sqlite3Strlen30(zName);
- pIndex = sqlite3AllocateIndexObject(db, pList->nExpr + 1,
+ nExtraCol = pPk ? pPk->nKeyCol : 1;
+ pIndex = sqlite3AllocateIndexObject(db, pList->nExpr + nExtraCol,
nName + nExtra + 1, &zExtra);
if( db->mallocFailed ){
goto exit_create_index;
pIndex->aSortOrder[i] = (u8)requestedSortOrder;
if( pTab->aCol[j].notNull==0 ) pIndex->uniqNotNull = 0;
}
- pIndex->aiColumn[i] = -1;
- pIndex->azColl[i] = "BINARY";
+ if( pPk ){
+ for(j=0; j<pPk->nKeyCol; j++, i++){
+ pIndex->aiColumn[i] = pPk->aiColumn[j];
+ pIndex->azColl[i] = pPk->azColl[j];
+ pIndex->aSortOrder[i] = pPk->aSortOrder[j];
+ }
+ }else{
+ pIndex->aiColumn[i] = -1;
+ pIndex->azColl[i] = "BINARY";
+ }
sqlite3DefaultRowEst(pIndex);
if( pParse->pNewTable==0 ) estimateIndexWidth(pIndex);
Table *pTab = pIdx->pTable;
int regBase;
int nCol;
+ Index *pPk;
if( piPartIdxLabel ){
if( pIdx->pPartIdxWhere ){
*piPartIdxLabel = 0;
}
}
- nCol = pIdx->nKeyCol;
- regBase = sqlite3GetTempRange(pParse, nCol+1);
- sqlite3VdbeAddOp2(v, OP_Rowid, iCur, regBase+nCol);
+ nCol = pIdx->nColumn;
+ regBase = sqlite3GetTempRange(pParse, nCol);
+ pPk = HasRowid(pTab) ? 0 : sqlite3PrimaryKeyIndex(pTab);
for(j=0; j<nCol; j++){
i16 idx = pIdx->aiColumn[j];
- if( idx==pTab->iPKey ){
- sqlite3VdbeAddOp2(v, OP_SCopy, regBase+nCol, regBase+j);
+ if( pPk ) idx = sqlite3ColumnOfIndex(pPk, idx);
+ if( idx<0 || idx==pTab->iPKey ){
+ sqlite3VdbeAddOp2(v, OP_Rowid, iCur, regBase+j);
}else{
sqlite3VdbeAddOp3(v, OP_Column, iCur, idx, regBase+j);
sqlite3ColumnDefault(v, pTab, idx, -1);
}else{
zAff = sqlite3IndexAffinityStr(v, pIdx);
}
- sqlite3VdbeAddOp3(v, OP_MakeRecord, regBase, nCol+1, regOut);
+ sqlite3VdbeAddOp3(v, OP_MakeRecord, regBase, nCol, regOut);
sqlite3VdbeChangeP4(v, -1, zAff, P4_TRANSIENT);
}
- sqlite3ReleaseTempRange(pParse, regBase, nCol+1);
+ sqlite3ReleaseTempRange(pParse, regBase, nCol);
return regBase;
}
int i, k;
int nHidden = 0;
Column *pCol;
- Index *pPk;
- for(pPk=pTab->pIndex; pPk && pPk->autoIndex!=2; pPk=pPk->pNext){}
+ Index *pPk = sqlite3PrimaryKeyIndex(pTab);
sqlite3VdbeSetNumCols(v, 6);
pParse->nMem = 6;
sqlite3CodeVerifySchema(pParse, iDb);
void sqlite3CommitInternalChanges(sqlite3*);
Table *sqlite3ResultSetOfSelect(Parse*,Select*);
void sqlite3OpenMasterTable(Parse *, int);
+Index *sqlite3PrimaryKeyIndex(Table*);
+i16 sqlite3ColumnOfIndex(Index*, i16);
void sqlite3StartTable(Parse*,Token*,Token*,int,int,int,int);
void sqlite3AddColumn(Parse*,Token*);
void sqlite3AddNotNull(Parse*, int);
}
}
assert( n==nKeyCol );
+ pIdx->aiColumn[n] = -1;
+ pIdx->azColl[n] = "BINARY";
/* Create the automatic index */
pKeyinfo = sqlite3IndexKeyinfo(pParse, pIdx);
pIdx = pLevel->u.pCovidx;
}
if( pIdx && !db->mallocFailed ){
- int k, j, last;
+ int k, last;
VdbeOp *pOp;
last = sqlite3VdbeCurrentAddr(v);
for(; k<last; k++, pOp++){
if( pOp->p1!=pLevel->iTabCur ) continue;
if( pOp->opcode==OP_Column ){
- for(j=0; j<pIdx->nColumn; j++){
- if( pOp->p2==pIdx->aiColumn[j] ){
- pOp->p2 = j;
- pOp->p1 = pLevel->iIdxCur;
- break;
- }
+ i16 x = sqlite3ColumnOfIndex(pIdx, pOp->p2);
+ if( x>=0 ){
+ pOp->p2 = x;
+ pOp->p1 = pLevel->iIdxCur;
}
- assert( (pLoop->wsFlags & WHERE_IDX_ONLY)==0 || j<pIdx->nColumn );
+ assert( (pLoop->wsFlags & WHERE_IDX_ONLY)==0 || x>=0 );
}else if( pOp->opcode==OP_Rowid ){
pOp->p1 = pLevel->iIdxCur;
pOp->opcode = OP_IdxRowid;