|
From: <dav...@us...> - 2006-05-04 04:43:23
|
Revision: 1346 Author: davidgewirtz Date: 2006-05-03 21:43:06 -0700 (Wed, 03 May 2006) ViewCVS: http://svn.sourceforge.net/frontierkernel/?rev=1346&view=rev Log Message: ----------- First candidate SQLite integration code. -- DG. Modified Paths: -------------- Frontier/branches/SQLite/Common/headers/langsqlite.h Frontier/branches/SQLite/Common/resources/Mac/kernelverbs.r Frontier/branches/SQLite/Common/resources/Win32/kernelverbs.rc Frontier/branches/SQLite/Common/source/langsqlite.c Modified: Frontier/branches/SQLite/Common/headers/langsqlite.h =================================================================== --- Frontier/branches/SQLite/Common/headers/langsqlite.h 2006-05-03 23:27:53 UTC (rev 1345) +++ Frontier/branches/SQLite/Common/headers/langsqlite.h 2006-05-04 04:43:06 UTC (rev 1346) @@ -31,26 +31,28 @@ extern boolean sqlitecloseverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-03-17 gewirtz */ -extern boolean sqliteexecverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-03-18 gewirtz */ +extern boolean sqlitecompilequeryverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqliteprepareverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqliteclearqueryverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqlitefinalizeverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqliteexecutequeryverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqlitestepverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqlitegetcolumncountverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqlitecolumncountverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqlitegetcolumntypeverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqlitecolumntypeverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqlitegetcolumnintverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqlitecolumnintverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqlitegetcolumndoubleverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqlitecolumndoubleverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqlitegetcolumntextverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqlitecolumntextverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqlitegetcolumnnameverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ -extern boolean sqlitecolumnnameverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-18 gewirtz */ +extern boolean sqlitegetcolumnverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-20 gewirtz */ +extern boolean sqlitegeterrormessageverb (hdltreenode, tyvaluerecord *, bigstring); /* 2006-04-20 gewirtz */ + extern boolean sqliteinitverbs (void); /* 2006-03-15 gewirtz */ /* boolean hmacmd5 (unsigned char *, int, unsigned char *, int, unsigned char *);*/ /* 2006-03-05 creedon */ Modified: Frontier/branches/SQLite/Common/resources/Mac/kernelverbs.r =================================================================== --- Frontier/branches/SQLite/Common/resources/Mac/kernelverbs.r 2006-05-03 23:27:53 UTC (rev 1345) +++ Frontier/branches/SQLite/Common/resources/Mac/kernelverbs.r 2006-05-04 04:43:06 UTC (rev 1346) @@ -1140,17 +1140,18 @@ "sqlite", false, { "open", - "exec", - "prepare", - "finalize", - "step", - "column_count", - "column_type", - "column_int", - "column_double", - "column_text", - "column_name", - "close" + "compileQuery", + "clearQuery", + "executeQuery", + "getColumnCount", + "getColumnType", + "getColumnInt", + "getColumnDouble", + "getColumnText", + "getColumnName", + "getColumn", + "getErrorMessage", + "getClose" } } }; Modified: Frontier/branches/SQLite/Common/resources/Win32/kernelverbs.rc =================================================================== --- Frontier/branches/SQLite/Common/resources/Win32/kernelverbs.rc 2006-05-03 23:27:53 UTC (rev 1345) +++ Frontier/branches/SQLite/Common/resources/Win32/kernelverbs.rc 2006-05-04 04:43:06 UTC (rev 1346) @@ -1078,18 +1078,19 @@ 1, // Number of "blocks" in this resource "sqlite\0", // Function Processor name false, // Window required - 12, // Count of verbs + 13, // Count of verbs "open\0", - "exec\0", - "prepare\0", - "finalize\0", - "step\0", - "column_count\0", - "column_type\0", - "column_int\0", - "column_double\0", - "column_text\0", - "column_name\0", + "compileQuery\0", + "clearQuery\0", + "executeQuery\0", + "getColumnCount\0", + "getColumnType\0", + "getColumnInt\0", + "getColumnDouble\0", + "getColumnText\0", + "getColumnName\0", + "getColumn\0", + "getErrorMessage\0", "close\0" END Modified: Frontier/branches/SQLite/Common/source/langsqlite.c =================================================================== --- Frontier/branches/SQLite/Common/source/langsqlite.c 2006-05-03 23:27:53 UTC (rev 1345) +++ Frontier/branches/SQLite/Common/source/langsqlite.c 2006-05-04 04:43:06 UTC (rev 1346) @@ -44,32 +44,44 @@ #include "langsqlite.h" #include <sqlite3.h> -typedef enum tysqliteverbtoken { /* verbs that are processed by langsqlite.c */ +/* Building SQLite into Frontier - openfunc, +The SQLite source distribution is compiled into the Frontier code as part of this +module. A key goal in this implementation was to avoid touching any of the SQLite +source files. SQLite is pretty complex in its coding, and I didn't want to take a +chance that any changes to the original SQLite code would muck up the database +functionality. - execfunc, +To include the latest SQLite distribution (we're implementing SQLite 3 here), +download the SQLite source code from http://www.sqlite.org/download.html. - preparefunc, +Move all the SQLite source files into the \Common\sqlite3 folder. If you need to +include new files in the SQLite project, be sure that shell.c and tclsqlite.c are +NOT included in the Frontier project. - finalizefunc, +That's it. For further tips, see the Frontier Lab Notebook article at: - stepfunc, +http://manila.zatz.com/frontierkernel/stories/storyReader$29 - columncountfunc, +-- DG - columntypefunc, +*/ - columnintfunc, +typedef enum tysqliteverbtoken { /* verbs that are processed by langsqlite.c */ - columndoublefunc, - - columntextfunc, - - columnnamefunc, - + openfunc, + compilequeryfunc, + clearqueryfunc, + executequeryfunc, + getcolumncountfunc, + getcolumntypefunc, + getcolumnintfunc, + getcolumndoublefunc, + getcolumntextfunc, + getcolumnnamefunc, + getcolumnfunc, + geterrormessagefunc, closefunc, - ctsqliteverbs } tysqliteverbtoken; @@ -83,66 +95,71 @@ hdltreenode hp1 = hparam1; tyvaluerecord *v = vreturned; - setbooleanvalue (false, v); /* by default, sqlite functions return false */ + setbooleanvalue (false, v); /* by default, sqlite functions return false */ switch (token) { - case openfunc: { /* 2006-03-14 gewirtz: open an SQLite db */ + case openfunc: { /* 2006-03-14 gewirtz: open an SQLite db */ return (sqliteopenverb (hp1, v, bserror)); } /* openfunc */ - case execfunc: { /* 2006-03-15 gewirtz: execute an SQLite statement */ + case compilequeryfunc: { /* 2006-04-18 gewirtz: prepare an SQLite statement */ - return (sqliteexecverb (hp1, v, bserror)); - } /* execfunc */ + return (sqlitecompilequeryverb (hp1, v, bserror)); + } /* compilequeryfunc */ - case preparefunc: { /* 2006-04-18 gewirtz: prepare an SQLite statement */ + case clearqueryfunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ - return (sqliteprepareverb (hp1, v, bserror)); - } /* preparefunc */ + return (sqliteclearqueryverb (hp1, v, bserror)); + } /* clearqueryfunc */ - case finalizefunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ + case executequeryfunc: { /* 2006-04-18 gewirtz: move the cursor one step after the query */ - return (sqlitefinalizeverb (hp1, v, bserror)); - } /* finalizefunc */ + return (sqliteexecutequeryverb (hp1, v, bserror)); + } /* executequeryfunc */ - case stepfunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ + case getcolumncountfunc: { /* 2006-04-18 gewirtz: get the number of columns */ - return (sqlitestepverb (hp1, v, bserror)); - } /* stepfunc */ + return (sqlitegetcolumncountverb (hp1, v, bserror)); + } /* getcolumncountfunc */ - case columncountfunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ + case getcolumntypefunc: { /* 2006-04-18 gewirtz: get the type of the referenced column */ + /* this version returns Frontier strings */ + return (sqlitegetcolumntypeverb (hp1, v, bserror)); + } /* getcolumntypefunc */ - return (sqlitecolumncountverb (hp1, v, bserror)); - } /* columncountfunc */ + case getcolumnintfunc: { /* 2006-04-18 gewirtz: get an int value from the column */ - case columntypefunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ + return (sqlitegetcolumnintverb (hp1, v, bserror)); + } /* getcolumnintfunc */ - return (sqlitecolumntypeverb (hp1, v, bserror)); - } /* columntypefunc */ + case getcolumndoublefunc: { /* 2006-04-18 gewirtz: get a double value from the column */ - case columnintfunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ + return (sqlitegetcolumndoubleverb (hp1, v, bserror)); + } /* getcolumndoublefunc */ - return (sqlitecolumnintverb (hp1, v, bserror)); - } /* columnintfunc */ + case getcolumntextfunc: { /* 2006-04-18 gewirtz: get a text value from the column */ - case columndoublefunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ + return (sqlitegetcolumntextverb (hp1, v, bserror)); + } /* getcolumntextfunc */ - return (sqlitecolumndoubleverb (hp1, v, bserror)); - } /* columndoublefunc */ + case getcolumnnamefunc: { /* 2006-04-18 gewirtz: get the field name of the column */ - case columntextfunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ + return (sqlitegetcolumnnameverb (hp1, v, bserror)); + } /* getcolumnnamefunc */ - return (sqlitecolumntextverb (hp1, v, bserror)); - } /* columntextfunc */ + case getcolumnfunc: { /* 2006-04-20 gewirtz: get the value of the column */ - case columnnamefunc: { /* 2006-04-18 gewirtz: finalize an SQLite statement */ + return (sqlitegetcolumnverb (hp1, v, bserror)); + } /* getcolumnfunc */ - return (sqlitecolumnnameverb (hp1, v, bserror)); - } /* columnnamefunc */ + case geterrormessagefunc: { /* 2006-04-20 gewirtz: get the SQLite error message */ - case closefunc: { /* 2006-03-15 gewirtz: close an SQLite db */ + return (sqlitegeterrormessageverb (hp1, v, bserror)); + } /* geterrormessagefunc */ + + case closefunc: { /* 2006-03-15 gewirtz: close an SQLite db */ return (sqlitecloseverb (hp1, v, bserror)); } /* closefunc */ @@ -194,349 +211,478 @@ boolean sqliteopenverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - int returnCode; /* return code from SQLite call */ + Handle dbfile; /* path to database file */ + sqlite3 *dbid; /* the SQLite database handle */ + int returnCode; /* return code from SQLite call */ - flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ + /* + sqlite.open(dbfile) + Action: opens a SQLite database + Params: a file path to the database file + Returns: a value that corresponds to the opened database ID + Usage: call in a try statement + Notes: do not pass the opened database ID across threads + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_open. + */ + + flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ + /* Enter the verb, convert the param to null-terminated string */ - if (!getexempttextvalue (hparam1, 1, &h)) + if (!getreadonlytextvalue (hparam1, 1, &dbfile)) return (false); - pushcharhandle (0x00, h); /* this should convert *h to a string */ + pushcharhandle (0x00, dbfile); /* convert *dbfile to a string */ /* Process the SQLite sequence */ - - returnCode = sqlite3_open(*h, &db); + returnCode = sqlite3_open(*dbfile, &dbid); if(returnCode) { - sqliteOpenError(sqlite3_errmsg(db), bserror); /* send database open error */ - disposehandle(h); /* get rid of the provided, original handle */ - sqlite3_close(db); + sqliteOpenError(sqlite3_errmsg(dbid), bserror); /* send database open error */ + sqlite3_close(dbid); return (false); } - return (setheapvalue ((Handle) db, longvaluetype, vreturned)); /* return the db address to the scripter */ + /* return the db address to the scripter */ + return (setheapvalue ((Handle) dbid, longvaluetype, vreturned)); } /* sqliteopenverb */ boolean sqlitecloseverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ + sqlite3 *dbid; /* the SQLite database handle */ int returnCode; /* return code from SQLite call */ + /* + sqlite.close(dbid) + + Action: close an SQLite database + Params: a database id + Returns: an SQLite result code + Usage: check result code for success or failure + Notes: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_close. + */ + flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ - if (!getlongvalue (hparam1, 1, &db)) /* Get the long value, which becomes the db pointer */ + if (!getlongvalue (hparam1, 1, (long *) &dbid)) /* Get the long value, which becomes the db pointer */ return (false); /* Process the SQLite sequence */ + returnCode = sqlite3_close(dbid); - returnCode = sqlite3_close(db); - if(returnCode != SQLITE_OK) { - sqliteDatabaseError(sqlite3_errmsg(db), bserror); /* send database error */ - disposehandle(h); /* get rid of the provided, original handle */ - return (false); - } - return setbooleanvalue (true, vreturned); + return setintvalue ((short) returnCode, vreturned); } /* sqlitecloseverb */ -boolean sqliteexecverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - int returnCode; /* return code from SQLite call */ +boolean sqlitecompilequeryverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + Handle query; /* the SQL query passed to the SQLite engine */ + sqlite3 *dbid; /* the SQLite database handle */ + sqlite3_stmt *queryid = 0; /* the compiled query */ + int returnCode; /* return code from SQLite call */ - if (!getlongvalue (hparam1, 1, &db)) /* Get the long value, which becomes the db pointer */ - return (false); + /* + sqlite.compileQuery(dbid, query) - flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ + Action: compile an SQLite query + Params: a database id and a query string + Returns: a query id + Usage: call in a try statement + Notes: do not pass the opened database ID across threads. - /* Enter the verb, convert the param to null-terminated string */ - if (!getexempttextvalue (hparam1, 2, &h)) - return (false); + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_prepare. - pushcharhandle (0x00, h); /* this should convert *h to a string */ - - /* Process the SQLite sequence */ - - returnCode = sqlite3_exec(db, *h, 0, 0, &zErrMsg); - if(returnCode != SQLITE_OK) { - sqliteDatabaseError(zErrMsg, bserror); /* send database open error */ - disposehandle(h); /* get rid of the provided, original handle */ - sqlite3_close(db); - return (false); - } - - return (setheapvalue ((Handle) db, longvaluetype, vreturned)); /* return the db address to the scripter */ - -} /* sqliteexecverb */ - -boolean sqliteprepareverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - const char **pzTail; /* remainder of the statement, not used, ignored for now */ - sqlite3_stmt *plineInfo = 0; /* the compiled query */ - int returnCode; /* return code from SQLite call */ - - /* Code that is a good example of prepare in use: - http://souptonuts.sourceforge.net/code/eatblob.c.html */ - if (!getlongvalue (hparam1, 1, &db)) /* Get the long value, which becomes the db pointer */ + if (!getlongvalue (hparam1, 1, (long *) &dbid)) /* Get the long value, which becomes the db pointer */ return (false); flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ /* Enter the verb, convert the param to null-terminated string */ - if (!getexempttextvalue (hparam1, 2, &h)) + if (!getreadonlytextvalue (hparam1, 2, &query)) return (false); - pushcharhandle (0x00, h); /* this should convert *h to a string */ - /* Process the SQLite sequence */ - - returnCode = sqlite3_prepare(db, *h, -1, &plineInfo, 0); - if(returnCode != SQLITE_OK || plineInfo == NULL) { - sqliteDatabaseError(sqlite3_errmsg(db), bserror); /* send database error */ - disposehandle(h); /* get rid of the provided, original handle */ - sqlite3_close(db); + returnCode = sqlite3_prepare(dbid, *query, gethandlesize(query), &queryid, 0); + if(returnCode != SQLITE_OK || queryid == NULL) { + sqliteDatabaseError(sqlite3_errmsg(dbid), bserror); /* send database error */ return (false); } - return (setheapvalue ((Handle) plineInfo, longvaluetype, vreturned)); /* return the db address to the scripter */ + return (setheapvalue ((Handle) queryid, longvaluetype, vreturned)); /* return the db address to the scripter */ -} /* sqliteprepareverb */ +} /* sqlitecompilequeryverb */ -boolean sqlitefinalizeverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - const char **pzTail; /* remainder of the statement, not used, ignored for now */ - sqlite3_stmt *plineInfo = 0; +boolean sqliteclearqueryverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + sqlite3_stmt *queryid; /* query id */ int returnCode; /* return code from SQLite call */ + /* + sqlite.clearQuery(queryid) + + Action: clear an SQLite query + Params: a query id + Returns: an SQLite result code + Notes: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_finalize. + */ + flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ - if (!getlongvalue (hparam1, 1, &plineInfo)) /* Get the long value, which becomes the pline pointer */ + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the queryid pointer */ return (false); /* Process the SQLite sequence */ + returnCode = sqlite3_finalize(queryid); - returnCode = sqlite3_finalize(plineInfo); - if(returnCode != SQLITE_OK) { - sqliteDatabaseError(zErrMsg, bserror); /* send database open error */ - sqlite3_close(db); - return (false); - } + return setintvalue ((short) returnCode, vreturned); - return setbooleanvalue (true, vreturned); +} /* sqliteclearqueryverb */ -} /* sqlitefinalizeverb */ - -boolean sqlitestepverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - const char **pzTail; /* remainder of the statement, not used, ignored for now */ - sqlite3_stmt *plineInfo = 0; +boolean sqliteexecutequeryverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + sqlite3_stmt *queryid; /* query id */ int returnCode; /* return code from SQLite call */ + /* + sqlite.executeQuery(queryid) + + Action: perform the query, moving the query cursor to the next row of results + Params: a query id + Returns: an SQLite result code + Notes: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_step. + */ + flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ - if (!getlongvalue (hparam1, 1, &plineInfo)) /* Get the long value, which becomes the pline pointer */ + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the pline pointer */ return (false); /* Process the SQLite sequence */ + returnCode = sqlite3_step(queryid); - returnCode = sqlite3_step(plineInfo); - if(returnCode == SQLITE_ERROR || returnCode == SQLITE_MISUSE) { - sqliteDatabaseError(zErrMsg, bserror); /* send database open error */ - sqlite3_close(db); - return (false); - } - return setintvalue ((short) returnCode, vreturned); -} /* sqlitestepverb */ +} /* sqliteexecutequeryverb */ -boolean sqlitecolumntypeverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - const char **pzTail; /* remainder of the statement, not used, ignored for now */ - sqlite3_stmt *plineInfo = 0; - int returnCode; /* return code from SQLite call */ +boolean sqlitegetcolumntypeverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + long columnNumber; /* column number */ + sqlite3_stmt *queryid; /* query id */ + int returnCode; /* return code from SQLite call */ - if (!getlongvalue (hparam1, 1, &plineInfo)) /* Get the long value, which becomes the pline pointer */ + /* + sqlite.getColumnType(queryid, columnNumber) + + Action: Retrieve the type of the specified column + Params: a query id and the number of the column (1 base) + Returns: an SQLite result code + Notes: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_column_type. + */ + + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the queryid pointer */ return (false); flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ /* Enter the verb, convert the param to null-terminated string */ - if (!getlongvalue (hparam1, 2, &h)) + if (!getlongvalue (hparam1, 2, &columnNumber)) return (false); /* Process the SQLite sequence */ + --columnNumber; /* Frontier uses base 1, but SQLite uses a base of 0 for its column numbering */ + returnCode = sqlite3_column_type(queryid, (int) columnNumber); - returnCode = sqlite3_column_type(plineInfo, h); + switch(returnCode) { - return setintvalue ((short) returnCode, vreturned); + case SQLITE_INTEGER: { + return setostypevalue (langgettypeid (longvaluetype), vreturned); + } + case SQLITE_FLOAT: { + return setostypevalue (langgettypeid (doublevaluetype), vreturned); + } + case SQLITE_TEXT: { + return setostypevalue (langgettypeid (stringvaluetype), vreturned); + } + case SQLITE_BLOB: { + return setostypevalue (langgettypeid (binaryvaluetype), vreturned); + } + case SQLITE_NULL: { + return setostypevalue (langgettypeid (novaluetype), vreturned); + } + default: { + /* SQLite spec says sqlite3_column_type only returns the above 5 types. But, + just in case it lied, we'll return an error type to help Frontier avoid + getting a case of return value indigestion. */ + return setostypevalue (langgettypeid (uninitializedvaluetype), vreturned); + } + } /* switch */ -} /* sqlitecolumntypeverb */ +} /* sqlitegetcolumntypeverb */ -boolean sqlitecolumnnameverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ +boolean sqlitegetcolumnnameverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + long columnNumber; /* column number */ + Handle returnH; const char *column_name; - sqlite3_stmt *plineInfo = 0; - int returnCode; /* return code from SQLite call */ + sqlite3_stmt *queryid; - if (!getlongvalue (hparam1, 1, &plineInfo)) /* Get the long value, which becomes the pline pointer */ + /* + sqlite.getColumnName(queryid, columnNumber) + + Action: Retrieve the name of the specified column + Params: a query id and the number of the column (1 base) + Returns: an SQLite result code + Notes: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_column_name. + */ + + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the pline pointer */ return (false); flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ /* Enter the verb, convert the param to null-terminated string */ - if (!getlongvalue (hparam1, 2, &h)) + if (!getlongvalue (hparam1, 2, &columnNumber)) return (false); /* Process the SQLite sequence */ + --columnNumber; /* Frontier uses base 1, but SQLite uses a base of 0 for its column numbering */ + column_name = sqlite3_column_name(queryid, (int) columnNumber); - column_name = sqlite3_column_name(plineInfo, h); - /* Exit the verb, converting column_name back to Frontier handle */ - - newfilledhandle (column_name, strlen (column_name), &returnH); + newfilledhandle ((ptrvoid) column_name, strlen (column_name), &returnH); return (setheapvalue (returnH, stringvaluetype, vreturned)); -} /* sqlitecolumnnameverb */ +} /* sqlitegetcolumnnameverb */ -boolean sqlitecolumncountverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - const char **pzTail; /* remainder of the statement, not used, ignored for now */ - sqlite3_stmt *plineInfo = 0; +boolean sqlitegetcolumncountverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + sqlite3_stmt *queryid; int returnCode; /* return code from SQLite call */ + /* + sqlite.getColumnCount(queryid) + + Action: Retrieve number of columns returned in a query + Params: a query id + Returns: the number of columns in the result set returned by the prepared SQL statement. + Notes: do not pass the opened database ID across threads. + returns 0 if pStmt is an SQL statement that does not return data (for example an UPDATE). + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_column_count. + */ flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ - if (!getlongvalue (hparam1, 1, &plineInfo)) /* Get the long value, which becomes the pline pointer */ + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the pline pointer */ return (false); /* Process the SQLite sequence */ + returnCode = sqlite3_column_count(queryid); - returnCode = sqlite3_column_count(plineInfo); - return setintvalue ((short) returnCode, vreturned); -} /* sqlitecolumncountverb */ +} /* sqlitegetcolumncountverb */ -boolean sqlitecolumnintverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - const char **pzTail; /* remainder of the statement, not used, ignored for now */ - sqlite3_stmt *plineInfo = 0; +boolean sqlitegetcolumnintverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + long columnNumber; + sqlite3_stmt *queryid; long returnCode; /* return code from SQLite call */ - if (!getlongvalue (hparam1, 1, &plineInfo)) /* Get the long value, which becomes the pline pointer */ + /* + sqlite.getColumnInt(queryid, columnNumber) + + Action: Retrieve the value of the specified integer-type column + Params: a query id and the number of the column (1 base) + Returns: an SQLite result code + Notes: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_column_int. + */ + + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the pline pointer */ return (false); flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ /* Enter the verb, convert the param to null-terminated string */ - if (!getlongvalue (hparam1, 2, &h)) + if (!getlongvalue (hparam1, 2, &columnNumber)) return (false); /* Process the SQLite sequence */ + --columnNumber; /* Frontier uses base 1, but SQLite uses a base of 0 for its column numbering */ + returnCode = sqlite3_column_int(queryid, (int) columnNumber); - returnCode = sqlite3_column_int(plineInfo, h); - return (setlongvalue ((long) returnCode, vreturned)); -} /* sqlitecolumnintverb */ +} /* sqlitegetcolumnintverb */ -boolean sqlitecolumndoubleverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - const char **pzTail; /* remainder of the statement, not used, ignored for now */ - sqlite3_stmt *plineInfo = 0; +boolean sqlitegetcolumndoubleverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + long columnNumber; + sqlite3_stmt *queryid; double returnCode; /* return code from SQLite call */ - if (!getlongvalue (hparam1, 1, &plineInfo)) /* Get the long value, which becomes the pline pointer */ + /* + sqlite.getColumnDouble(queryid, columnNumber) + + Action: Retrieve the value of the specified double-type column + Params: a query id and the number of the column (1 base) + Returns: an SQLite result code + Notes: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_column_double. + */ + + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the pline pointer */ return (false); flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ /* Enter the verb, convert the param to null-terminated string */ - if (!getlongvalue (hparam1, 2, &h)) + if (!getlongvalue (hparam1, 2, &columnNumber)) return (false); /* Process the SQLite sequence */ + --columnNumber; /* Frontier uses base 1, but SQLite uses a base of 0 for its column numbering */ + returnCode = sqlite3_column_double(queryid, (int) columnNumber); - returnCode = sqlite3_column_double(plineInfo, h); - return (setlongvalue ((double) returnCode, vreturned)); -} /* sqlitecolumndoubleverb */ +} /* sqlitegetcolumndoubleverb */ -boolean sqlitecolumntextverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { - Handle h = nil; - Handle returnH = nil; - char *zErrMsg = 0; /* SQLite's error message */ - sqlite3 *db; /* the SQLite DB handle, be careful to not pass this across threads */ - const char **pzTail; /* remainder of the statement, not used, ignored for now */ - sqlite3_stmt *plineInfo = 0; - int returnCode; /* return code from SQLite call */ +boolean sqlitegetcolumntextverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + long columnNumber; + sqlite3_stmt *queryid; + Handle returnH; const unsigned char *column_text; - if (!getlongvalue (hparam1, 1, &plineInfo)) /* Get the long value, which becomes the pline pointer */ + /* + sqlite.getColumnText(queryid, columnNumber) + + Action: Retrieve the value of the specified text-type column + Params: a query id and the number of the column (1 base) + Returns: an SQLite result code + Notes: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_column_text. + */ + + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the pline pointer */ return (false); flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ /* Enter the verb, convert the param to null-terminated string */ - if (!getlongvalue (hparam1, 2, &h)) + if (!getlongvalue (hparam1, 2, &columnNumber)) return (false); /* Process the SQLite sequence */ + --columnNumber; /* Frontier uses base 1, but SQLite uses a base of 0 for its column numbering */ + column_text = sqlite3_column_text(queryid, (int) columnNumber); - column_text = sqlite3_column_text(plineInfo, h); - /* Exit the verb, converting column_name back to Frontier handle */ - - newfilledhandle (column_text, strlen (column_text), &returnH); + newfilledhandle ((ptrvoid) column_text, strlen (column_text), &returnH); return (setheapvalue (returnH, stringvaluetype, vreturned)); -} /* sqlitecolumntextverb */ +} /* sqlitegetcolumntextverb */ -/* boolean hmacmd5 (unsigned char * text, int text_len, unsigned char * key, int key_len, unsigned char * digest) - - function code went here +boolean sqlitegetcolumnverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + long columnNumber; /* column number */ + sqlite3_stmt *queryid; /* query id */ + int returnCode; /* return code from SQLite call */ + Handle returnH; + const unsigned char *column_text; -*/ + /* + sqlite.getColumn(queryid, columnNumber) + Action: Retrieve the value of the specified column element + Params: a query id and the number of the column (1 base) + Returns: an SQLite result code + Notes: do not pass the opened database ID across threads. + this implementation does not support blobs. If a blob column is requested, 0 is returned. -/* boolean hmacsha1 (unsigned char * text, int text_len, unsigned char * key, int key_len, unsigned char * digest) + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_column_type. + */ - function code went here + if (!getlongvalue (hparam1, 1, (long *) &queryid)) /* Get the long value, which becomes the queryid pointer */ + return (false); -*/ \ No newline at end of file + flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ + + /* Enter the verb, convert the param to null-terminated string */ + if (!getlongvalue (hparam1, 2, &columnNumber)) + return (false); + + /* Process the SQLite sequence */ + --columnNumber; /* Frontier uses base 1, but SQLite uses a base of 0 for its column numbering */ + returnCode = sqlite3_column_type(queryid, (int) columnNumber); + + switch(returnCode) { + + case SQLITE_INTEGER: { + returnCode = sqlite3_column_int(queryid, (int) columnNumber); + return (setlongvalue ((long) returnCode, vreturned)); + } + case SQLITE_FLOAT: { + returnCode = sqlite3_column_double(queryid, (int) columnNumber); + return (setlongvalue ((double) returnCode, vreturned)); + } + case SQLITE_TEXT: { + column_text = sqlite3_column_text(queryid, (int) columnNumber); + + /* Exit the verb, converting column_name back to Frontier handle */ + newfilledhandle ((ptrvoid) column_text, strlen (column_text), &returnH); + return (setheapvalue (returnH, stringvaluetype, vreturned)); + } + case SQLITE_BLOB: { + return (setlongvalue ((long) 0, vreturned)); + } + case SQLITE_NULL: { + return (setlongvalue ((long) 0, vreturned)); + } + default: { + /* SQLite spec says sqlite3_column_type only returns the above 5 types. But, + just in case it lied, we'll return an error type to help Frontier avoid + getting a case of return value indigestion. */ + return (setlongvalue ((long) 0, vreturned)); + } + } /* switch */ + +} /* sqlitegetcolumntext */ + +boolean sqlitegeterrormessageverb (hdltreenode hparam1, tyvaluerecord *vreturned, bigstring bserror) { + const char *sqliteError; /* pointer to the error message */ + sqlite3 *db; /* the SQLite database handle */ + Handle returnH = nil; /* The handle being returned back to Frontier */ + + /* + Frontier verb: sqlite.getErrorMessage(dbfile) + + Returns the error message for the most recent SQLite API call. + Takes a database ID. + Returns a string containing the error message. + NOTE: do not pass the opened database ID across threads. + + SQLite docs: http://www.sqlite.org/capi3ref.html#sqlite3_errmsg. + */ + + flnextparamislast = true; /* makes sure Frontier throws an error if more than one param is passed */ + + if (!getlongvalue (hparam1, 1, (long *) &db)) /* Get the long value, which becomes the db pointer */ + return (false); + + /* Process the SQLite sequence */ + sqliteError = sqlite3_errmsg(db); + + /* Exit the verb, converting errMsg back to Frontier handle */ + newfilledhandle ((ptrvoid) sqliteError, strlen (sqliteError), &returnH); + return (setheapvalue (returnH, stringvaluetype, vreturned)); + +} /* sqlitegeterrormessageverb */ \ No newline at end of file This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |