Many hyperlinks are disabled.
Use anonymous login
to enable hyperlinks.
Overview
Comment: | Allow virtual table implementations to overload function that use a column of the virtual table as their first argument. Untested. (CVS 3322) |
---|---|
Downloads: | Tarball | ZIP archive |
Timelines: | family | ancestors | descendants | both | trunk |
Files: | files | file ages | folders |
SHA1: |
12cc7af4b6b8b4f1a43d962fbafde8cb |
User & Date: | drh 2006-07-08 17:06:44.000 |
Context
2006-07-08
| ||
18:09 | Add tests and minor fixes to the xFindFunction method of virtual tables. (CVS 3323) (check-in: 3c4233e074 user: drh tags: trunk) | |
17:06 | Allow virtual table implementations to overload function that use a column of the virtual table as their first argument. Untested. (CVS 3322) (check-in: 12cc7af4b6 user: drh tags: trunk) | |
2006-07-06
| ||
17:08 | Make the sqlite3_enable_load_extension() interface accessible from the TCL bindings. (CVS 3321) (check-in: ce96b890bb user: drh tags: trunk) | |
Changes
Changes to src/expr.c.
︙ | ︙ | |||
8 9 10 11 12 13 14 | ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** This file contains routines used for analyzing expressions and ** for generating VDBE code that evaluates expressions in SQLite. ** | | | 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** This file contains routines used for analyzing expressions and ** for generating VDBE code that evaluates expressions in SQLite. ** ** $Id: expr.c,v 1.263 2006/07/08 17:06:44 drh Exp $ */ #include "sqliteInt.h" #include <ctype.h> /* ** Return the 'affinity' of the expression pExpr if any. ** |
︙ | ︙ | |||
1670 1671 1672 1673 1674 1675 1676 1677 1678 1679 1680 1681 1682 1683 | u8 enc = ENC(pParse->db); CollSeq *pColl = 0; zId = (char*)pExpr->token.z; nId = pExpr->token.n; pDef = sqlite3FindFunction(pParse->db, zId, nId, nExpr, enc, 0); assert( pDef!=0 ); nExpr = sqlite3ExprCodeExprList(pParse, pList); for(i=0; i<nExpr && i<32; i++){ if( sqlite3ExprIsConstant(pList->a[i].pExpr) ){ constMask |= (1<<i); } if( pDef->needCollSeq && !pColl ){ pColl = sqlite3ExprCollSeq(pParse, pList->a[i].pExpr); } | > > > > > | 1670 1671 1672 1673 1674 1675 1676 1677 1678 1679 1680 1681 1682 1683 1684 1685 1686 1687 1688 | u8 enc = ENC(pParse->db); CollSeq *pColl = 0; zId = (char*)pExpr->token.z; nId = pExpr->token.n; pDef = sqlite3FindFunction(pParse->db, zId, nId, nExpr, enc, 0); assert( pDef!=0 ); nExpr = sqlite3ExprCodeExprList(pParse, pList); #ifndef SQLITE_OMIT_VIRTUALTABLE if( nExpr>0 ){ pDef = sqlite3VtabOverloadFunction(pDef, nExpr, pList->a[0].pExpr); } #endif for(i=0; i<nExpr && i<32; i++){ if( sqlite3ExprIsConstant(pList->a[i].pExpr) ){ constMask |= (1<<i); } if( pDef->needCollSeq && !pColl ){ pColl = sqlite3ExprCollSeq(pParse, pList->a[i].pExpr); } |
︙ | ︙ |
Changes to src/sqlite.h.in.
︙ | ︙ | |||
8 9 10 11 12 13 14 | ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** This header file defines the interface that the SQLite library ** presents to client programs. ** | | | 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** This header file defines the interface that the SQLite library ** presents to client programs. ** ** @(#) $Id: sqlite.h.in,v 1.186 2006/07/08 17:06:44 drh Exp $ */ #ifndef _SQLITE3_H_ #define _SQLITE3_H_ #include <stdarg.h> /* Needed for the definition of va_list */ /* ** Make sure we can call this stuff from C++. |
︙ | ︙ | |||
1561 1562 1563 1564 1565 1566 1567 1568 1569 1570 1571 1572 1573 1574 | int (*xColumn)(sqlite3_vtab_cursor*, sqlite3_context*, int); int (*xRowid)(sqlite3_vtab_cursor*, sqlite_int64 *pRowid); int (*xUpdate)(sqlite3_vtab *, int, sqlite3_value **, sqlite_int64 *); int (*xBegin)(sqlite3_vtab *pVTab); int (*xSync)(sqlite3_vtab *pVTab); int (*xCommit)(sqlite3_vtab *pVTab); int (*xRollback)(sqlite3_vtab *pVTab); }; /* ** The sqlite3_index_info structure and its substructures is used to ** pass information into and receive the reply from the xBestIndex ** method of an sqlite3_module. The fields under **Inputs** are the ** inputs to xBestIndex and are read-only. xBestIndex inserts its | > > > | 1561 1562 1563 1564 1565 1566 1567 1568 1569 1570 1571 1572 1573 1574 1575 1576 1577 | int (*xColumn)(sqlite3_vtab_cursor*, sqlite3_context*, int); int (*xRowid)(sqlite3_vtab_cursor*, sqlite_int64 *pRowid); int (*xUpdate)(sqlite3_vtab *, int, sqlite3_value **, sqlite_int64 *); int (*xBegin)(sqlite3_vtab *pVTab); int (*xSync)(sqlite3_vtab *pVTab); int (*xCommit)(sqlite3_vtab *pVTab); int (*xRollback)(sqlite3_vtab *pVTab); int (*xFindFunction)(sqlite3_vtab *pVtab, int nArg, const char *zName, int (**pxFunc)(sqlite3_context*,int,sqlite3_value**), void **ppArg, int *piPrefEnc); }; /* ** The sqlite3_index_info structure and its substructures is used to ** pass information into and receive the reply from the xBestIndex ** method of an sqlite3_module. The fields under **Inputs** are the ** inputs to xBestIndex and are read-only. xBestIndex inserts its |
︙ | ︙ |
Changes to src/sqliteInt.h.
1 2 3 4 5 6 7 8 9 10 11 12 13 | /* ** 2001 September 15 ** ** The author disclaims copyright to this source code. In place of ** a legal notice, here is a blessing: ** ** May you do good and not evil. ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** Internal interface definitions for SQLite. ** | | | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | /* ** 2001 September 15 ** ** The author disclaims copyright to this source code. In place of ** a legal notice, here is a blessing: ** ** May you do good and not evil. ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** Internal interface definitions for SQLite. ** ** @(#) $Id: sqliteInt.h,v 1.518 2006/07/08 17:06:44 drh Exp $ */ #ifndef _SQLITEINT_H_ #define _SQLITEINT_H_ /* ** Extra interface definitions for those who need them */ |
︙ | ︙ | |||
582 583 584 585 586 587 588 589 590 591 592 593 594 595 | }; /* ** Possible values for FuncDef.flags */ #define SQLITE_FUNC_LIKE 0x01 /* Candidate for the LIKE optimization */ #define SQLITE_FUNC_CASE 0x02 /* Case-sensitive LIKE-type function */ /* ** information about each column of an SQL table is held in an instance ** of this structure. */ struct Column { char *zName; /* Name of this column */ | > | 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 | }; /* ** Possible values for FuncDef.flags */ #define SQLITE_FUNC_LIKE 0x01 /* Candidate for the LIKE optimization */ #define SQLITE_FUNC_CASE 0x02 /* Case-sensitive LIKE-type function */ #define SQLITE_FUNC_EPHEM 0x04 /* Ephermeral. Delete with VDBE */ /* ** information about each column of an SQL table is held in an instance ** of this structure. */ struct Column { char *zName; /* Name of this column */ |
︙ | ︙ | |||
1857 1858 1859 1860 1861 1862 1863 1864 1865 1866 1867 1868 1869 | void sqlite3VtabFinishParse(Parse*, Token*); void sqlite3VtabArgInit(Parse*); void sqlite3VtabArgExtend(Parse*, Token*); int sqlite3VtabCallCreate(sqlite3*, int, const char *, char **); int sqlite3VtabCallConnect(Parse*, Table*); int sqlite3VtabCallDestroy(sqlite3*, int, const char *); int sqlite3VtabBegin(sqlite3 *, sqlite3_vtab *); #ifdef SQLITE_SSE #include "sseInt.h" #endif #endif | > | 1858 1859 1860 1861 1862 1863 1864 1865 1866 1867 1868 1869 1870 1871 | void sqlite3VtabFinishParse(Parse*, Token*); void sqlite3VtabArgInit(Parse*); void sqlite3VtabArgExtend(Parse*, Token*); int sqlite3VtabCallCreate(sqlite3*, int, const char *, char **); int sqlite3VtabCallConnect(Parse*, Table*); int sqlite3VtabCallDestroy(sqlite3*, int, const char *); int sqlite3VtabBegin(sqlite3 *, sqlite3_vtab *); FuncDef *sqlite3VtabOverloadFunction(FuncDef*, int nArg, Expr*); #ifdef SQLITE_SSE #include "sseInt.h" #endif #endif |
Changes to src/test8.c.
︙ | ︙ | |||
9 10 11 12 13 14 15 | ** May you share freely, never taking more than you give. ** ************************************************************************* ** Code for testing the virtual table interfaces. This code ** is not included in the SQLite library. It is used for automated ** testing of the SQLite library. ** | | | 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | ** May you share freely, never taking more than you give. ** ************************************************************************* ** Code for testing the virtual table interfaces. This code ** is not included in the SQLite library. It is used for automated ** testing of the SQLite library. ** ** $Id: test8.c,v 1.39 2006/07/08 17:06:44 drh Exp $ */ #include "sqliteInt.h" #include "tcl.h" #include "os.h" #include <stdlib.h> #include <string.h> |
︙ | ︙ | |||
914 915 916 917 918 919 920 | echoEof, /* xEof */ echoColumn, /* xColumn - read data */ echoRowid, /* xRowid - read data */ echoUpdate, /* xUpdate - write data */ echoBegin, /* xBegin - begin transaction */ echoSync, /* xSync - sync transaction */ echoCommit, /* xCommit - commit transaction */ | | > | 914 915 916 917 918 919 920 921 922 923 924 925 926 927 928 929 | echoEof, /* xEof */ echoColumn, /* xColumn - read data */ echoRowid, /* xRowid - read data */ echoUpdate, /* xUpdate - write data */ echoBegin, /* xBegin - begin transaction */ echoSync, /* xSync - sync transaction */ echoCommit, /* xCommit - commit transaction */ echoRollback, /* xRollback - rollback transaction */ 0, /* xFindMethod - function overloading */ }; /* ** Decode a pointer to an sqlite3 object. */ static int getDbPointer(Tcl_Interp *interp, const char *zA, sqlite3 **ppDb){ *ppDb = (sqlite3*)sqlite3TextToPtr(zA); |
︙ | ︙ |
Changes to src/test_schema.c.
︙ | ︙ | |||
9 10 11 12 13 14 15 | ** May you share freely, never taking more than you give. ** ************************************************************************* ** Code for testing the virtual table interfaces. This code ** is not included in the SQLite library. It is used for automated ** testing of the SQLite library. ** | | | 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | ** May you share freely, never taking more than you give. ** ************************************************************************* ** Code for testing the virtual table interfaces. This code ** is not included in the SQLite library. It is used for automated ** testing of the SQLite library. ** ** $Id: test_schema.c,v 1.9 2006/07/08 17:06:44 drh Exp $ */ /* The code in this file defines a sqlite3 virtual-table module that ** provides a read-only view of the current database schema. There is one ** row in the schema table for each column in the database schema. */ #define SCHEMA \ |
︙ | ︙ | |||
277 278 279 280 281 282 283 284 285 286 287 288 289 290 | schemaOpen, /* xOpen - open a cursor */ schemaClose, /* xClose - close a cursor */ schemaFilter, /* xFilter - configure scan constraints */ schemaNext, /* xNext - advance a cursor */ schemaEof, /* xEof */ schemaColumn, /* xColumn - read data */ schemaRowid, /* xRowid - read data */ }; #ifdef SQLITE_TEST /* ** Decode a pointer to an sqlite3 object. | > > > > > > | 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 | schemaOpen, /* xOpen - open a cursor */ schemaClose, /* xClose - close a cursor */ schemaFilter, /* xFilter - configure scan constraints */ schemaNext, /* xNext - advance a cursor */ schemaEof, /* xEof */ schemaColumn, /* xColumn - read data */ schemaRowid, /* xRowid - read data */ 0, /* xUpdate */ 0, /* xBegin */ 0, /* xSync */ 0, /* xCommit */ 0, /* xRollback */ 0, /* xFindMethod */ }; #ifdef SQLITE_TEST /* ** Decode a pointer to an sqlite3 object. |
︙ | ︙ |
Changes to src/test_tclvar.c.
︙ | ︙ | |||
12 13 14 15 16 17 18 | ** Code for testing the virtual table interfaces. This code ** is not included in the SQLite library. It is used for automated ** testing of the SQLite library. ** ** The emphasis of this file is a virtual table that provides ** access to TCL variables. ** | | | 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 | ** Code for testing the virtual table interfaces. This code ** is not included in the SQLite library. It is used for automated ** testing of the SQLite library. ** ** The emphasis of this file is a virtual table that provides ** access to TCL variables. ** ** $Id: test_tclvar.c,v 1.7 2006/07/08 17:06:44 drh Exp $ */ #include "sqliteInt.h" #include "tcl.h" #include "os.h" #include <stdlib.h> #include <string.h> |
︙ | ︙ | |||
263 264 265 266 267 268 269 | tclvarEof, /* xEof - check for end of scan */ tclvarColumn, /* xColumn - read data */ tclvarRowid, /* xRowid - read data */ 0, /* xUpdate */ 0, /* xBegin */ 0, /* xSync */ 0, /* xCommit */ | | > | 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 | tclvarEof, /* xEof - check for end of scan */ tclvarColumn, /* xColumn - read data */ tclvarRowid, /* xRowid - read data */ 0, /* xUpdate */ 0, /* xBegin */ 0, /* xSync */ 0, /* xCommit */ 0, /* xRollback */ 0, /* xFindMethod */ }; /* ** Decode a pointer to an sqlite3 object. */ static int getDbPointer(Tcl_Interp *interp, const char *zA, sqlite3 **ppDb){ *ppDb = (sqlite3*)sqlite3TextToPtr(zA); |
︙ | ︙ |
Changes to src/vdbeaux.c.
︙ | ︙ | |||
369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 | ** Change the P2 operand of instruction addr so that it points to ** the address of the next instruction to be coded. */ void sqlite3VdbeJumpHere(Vdbe *p, int addr){ sqlite3VdbeChangeP2(p, addr, p->nOp); } /* ** Delete a P3 value if necessary. */ static void freeP3(int p3type, void *p3){ if( p3 ){ switch( p3type ){ case P3_DYNAMIC: case P3_KEYINFO: case P3_KEYINFO_HANDOFF: { sqliteFree(p3); break; } case P3_MPRINTF: { sqlite3_free(p3); break; } case P3_VDBEFUNC: { VdbeFunc *pVdbeFunc = (VdbeFunc *)p3; sqlite3VdbeDeleteAuxData(pVdbeFunc, 0); sqliteFree(pVdbeFunc); break; } case P3_MEM: { sqlite3ValueFree((sqlite3_value*)p3); break; } } } | > > > > > > > > > > > > > > > > | 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 | ** Change the P2 operand of instruction addr so that it points to ** the address of the next instruction to be coded. */ void sqlite3VdbeJumpHere(Vdbe *p, int addr){ sqlite3VdbeChangeP2(p, addr, p->nOp); } /* ** If the input FuncDef structure is ephemeral, then free it. If ** the FuncDef is not ephermal, then do nothing. */ static void freeEphemeralFunction(FuncDef *pDef){ if( pDef && (pDef->flags & SQLITE_FUNC_EPHEM)!=0 ){ sqliteFree(pDef); } } /* ** Delete a P3 value if necessary. */ static void freeP3(int p3type, void *p3){ if( p3 ){ switch( p3type ){ case P3_DYNAMIC: case P3_KEYINFO: case P3_KEYINFO_HANDOFF: { sqliteFree(p3); break; } case P3_MPRINTF: { sqlite3_free(p3); break; } case P3_VDBEFUNC: { VdbeFunc *pVdbeFunc = (VdbeFunc *)p3; freeEphemeralFunction(pVdbeFunc->pFunc); sqlite3VdbeDeleteAuxData(pVdbeFunc, 0); sqliteFree(pVdbeFunc); break; } case P3_FUNCDEF: { freeEphemeralFunction((FuncDef*)p3); break; } case P3_MEM: { sqlite3ValueFree((sqlite3_value*)p3); break; } } } |
︙ | ︙ |
Changes to src/vtab.c.
1 2 3 4 5 6 7 8 9 10 11 12 13 | /* ** 2006 June 10 ** ** The author disclaims copyright to this source code. In place of ** a legal notice, here is a blessing: ** ** May you do good and not evil. ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** This file contains code used to help implement virtual tables. ** | | | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | /* ** 2006 June 10 ** ** The author disclaims copyright to this source code. In place of ** a legal notice, here is a blessing: ** ** May you do good and not evil. ** May you find forgiveness for yourself and forgive others. ** May you share freely, never taking more than you give. ** ************************************************************************* ** This file contains code used to help implement virtual tables. ** ** $Id: vtab.c,v 1.26 2006/07/08 17:06:44 drh Exp $ */ #ifndef SQLITE_OMIT_VIRTUALTABLE #include "sqliteInt.h" /* ** External API function used to create a new virtual-table module. */ |
︙ | ︙ | |||
568 569 570 571 572 573 574 575 576 | return rc; } rc = addToVTrans(db, pVtab); } return rc; } #endif /* SQLITE_OMIT_VIRTUALTABLE */ | > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > | 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 603 604 605 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 | return rc; } rc = addToVTrans(db, pVtab); } return rc; } /* ** The first parameter (pDef) is a function implementation. The ** second parameter (pExpr) is the first argument to this function. ** If pExpr is a column in a virtual table, then let the virtual ** table implementation have an opportunity to overload the function. ** ** This routine is used to allow virtual table implementations to ** overload MATCH, LIKE, GLOB, and REGEXP operators. ** ** Return either the pDef argument (indicating no change) or a ** new FuncDef structure that is marked as ephemeral using the ** SQLITE_FUNC_EPHEM flag. */ FuncDef *sqlite3VtabOverloadFunction( FuncDef *pDef, /* Function to possibly overload */ int nArg, /* Number of arguments to the function */ Expr *pExpr /* First argument to the function */ ){ Table *pTab; sqlite3_vtab *pVtab; sqlite3_module *pMod; int (*xFunc)(sqlite3_context*,int,sqlite3_value**); void *pArg; int iEnc; int rc; FuncDef *pNew; /* Check to see the left operand is a column in a virtual table */ if( pExpr==0 ) return pDef; if( pExpr->op!=TK_COLUMN ) return pDef; pTab = pExpr->pTab; if( pTab==0 ) return pDef; if( !pTab->isVirtual ) return pDef; pVtab = pTab->pVtab; assert( pVtab!=0 ); assert( pVtab->pModule!=0 ); pMod = pVtab->pModule; if( pMod->xFindFunction==0 ) return pDef; /* Call the xFuncFunction method on the virtual table implementation ** to see if the implementation wants to overload this function */ if( pMod->xFindFunction(pVtab, nArg, pDef->zName, &xFunc, &pArg, &iEnc)==0 ){ return pDef; } /* Create a new ephemeral function definition for the overloaded ** function */ pNew = sqliteMalloc( sizeof(*pNew) + strlen(pDef->zName) ); if( pNew==0 ){ return pDef; } *pNew = *pDef; strcpy(pNew->zName, pDef->zName); pNew->xFunc = xFunc; pNew->pUserData = pArg; pNew->iPrefEnc = iEnc; pNew->flags |= SQLITE_FUNC_EPHEM; return pNew; } #endif /* SQLITE_OMIT_VIRTUALTABLE */ |