⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 tclsqlite.c

📁 最新的sqlite3.6.2源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
#endif  return pVal;}/*** This routine reads a line of text from FILE in, stores** the text in memory obtained from malloc() and returns a pointer** to the text.  NULL is returned at end of file, or if malloc()** fails.**** The interface is like "readline" but no command-line editing** is done.**** copied from shell.c from '.import' command*/static char *local_getline(char *zPrompt, FILE *in){  char *zLine;  int nLine;  int n;  int eol;  nLine = 100;  zLine = malloc( nLine );  if( zLine==0 ) return 0;  n = 0;  eol = 0;  while( !eol ){    if( n+100>nLine ){      nLine = nLine*2 + 100;      zLine = realloc(zLine, nLine);      if( zLine==0 ) return 0;    }    if( fgets(&zLine[n], nLine - n, in)==0 ){      if( n==0 ){        free(zLine);        return 0;      }      zLine[n] = 0;      eol = 1;      break;    }    while( zLine[n] ){ n++; }    if( n>0 && zLine[n-1]=='\n' ){      n--;      zLine[n] = 0;      eol = 1;    }  }  zLine = realloc( zLine, n+1 );  return zLine;}/*** Figure out the column names for the data returned by the statement** passed as the second argument.**** If parameter papColName is not NULL, then *papColName is set to point** at an array allocated using Tcl_Alloc(). It is the callers responsibility** to free this array using Tcl_Free(), and to decrement the reference** count of each Tcl_Obj* member of the array.**** The return value of this function is the number of columns of data** returned by pStmt (and hence the size of the *papColName array).**** If pArray is not NULL, then it contains the name of a Tcl array** variable. The "*" member of this array is set to a list containing** the names of the columns returned by the statement, in order from** left to right. e.g. if the names of the returned columns are a, b and** c, it does the equivalent of the tcl command:****     set ${pArray}(*) {a b c}*/static intcomputeColumnNames(  Tcl_Interp *interp,   sqlite3_stmt *pStmt,              /* SQL statement */  Tcl_Obj ***papColName,            /* OUT: Array of column names */  Tcl_Obj *pArray                   /* Name of array variable (may be null) */){  int nCol;  /* Compute column names */  nCol = sqlite3_column_count(pStmt);  if( papColName ){    int i;    Tcl_Obj **apColName = (Tcl_Obj**)Tcl_Alloc( sizeof(Tcl_Obj*)*nCol );    for(i=0; i<nCol; i++){      apColName[i] = dbTextToObj(sqlite3_column_name(pStmt,i));      Tcl_IncrRefCount(apColName[i]);    }    /* If results are being stored in an array variable, then create    ** the array(*) entry for that array    */    if( pArray ){      Tcl_Obj *pColList = Tcl_NewObj();      Tcl_Obj *pStar = Tcl_NewStringObj("*", -1);      Tcl_IncrRefCount(pColList);      for(i=0; i<nCol; i++){        Tcl_ListObjAppendElement(interp, pColList, apColName[i]);      }      Tcl_IncrRefCount(pStar);      Tcl_ObjSetVar2(interp, pArray, pStar, pColList,0);      Tcl_DecrRefCount(pColList);      Tcl_DecrRefCount(pStar);    }    *papColName = apColName;  }  return nCol;}/*** The "sqlite" command below creates a new Tcl command for each** connection it opens to an SQLite database.  This routine is invoked** whenever one of those connection-specific commands is executed** in Tcl.  For example, if you run Tcl code like this:****       sqlite3 db1  "my_database"**       db1 close**** The first command opens a connection to the "my_database" database** and calls that connection "db1".  The second command causes this** subroutine to be invoked.*/static int DbObjCmd(void *cd, Tcl_Interp *interp, int objc,Tcl_Obj *const*objv){  SqliteDb *pDb = (SqliteDb*)cd;  int choice;  int rc = TCL_OK;  static const char *DB_strs[] = {    "authorizer",         "busy",              "cache",    "changes",            "close",             "collate",    "collation_needed",   "commit_hook",       "complete",    "copy",               "enable_load_extension","errorcode",    "eval",               "exists",            "function",    "incrblob",           "interrupt",         "last_insert_rowid",    "nullvalue",          "onecolumn",         "profile",    "progress",           "rekey",             "rollback_hook",    "timeout",            "total_changes",     "trace",    "transaction",        "update_hook",       "version",    0                      };  enum DB_enum {    DB_AUTHORIZER,        DB_BUSY,             DB_CACHE,    DB_CHANGES,           DB_CLOSE,            DB_COLLATE,    DB_COLLATION_NEEDED,  DB_COMMIT_HOOK,      DB_COMPLETE,    DB_COPY,              DB_ENABLE_LOAD_EXTENSION,DB_ERRORCODE,    DB_EVAL,              DB_EXISTS,           DB_FUNCTION,    DB_INCRBLOB,          DB_INTERRUPT,        DB_LAST_INSERT_ROWID,    DB_NULLVALUE,         DB_ONECOLUMN,        DB_PROFILE,    DB_PROGRESS,          DB_REKEY,            DB_ROLLBACK_HOOK,    DB_TIMEOUT,           DB_TOTAL_CHANGES,    DB_TRACE,    DB_TRANSACTION,       DB_UPDATE_HOOK,      DB_VERSION  };  /* don't leave trailing commas on DB_enum, it confuses the AIX xlc compiler */  if( objc<2 ){    Tcl_WrongNumArgs(interp, 1, objv, "SUBCOMMAND ...");    return TCL_ERROR;  }  if( Tcl_GetIndexFromObj(interp, objv[1], DB_strs, "option", 0, &choice) ){    return TCL_ERROR;  }  switch( (enum DB_enum)choice ){  /*    $db authorizer ?CALLBACK?  **  ** Invoke the given callback to authorize each SQL operation as it is  ** compiled.  5 arguments are appended to the callback before it is  ** invoked:  **  **   (1) The authorization type (ex: SQLITE_CREATE_TABLE, SQLITE_INSERT, ...)  **   (2) First descriptive name (depends on authorization type)  **   (3) Second descriptive name  **   (4) Name of the database (ex: "main", "temp")  **   (5) Name of trigger that is doing the access  **  ** The callback should return on of the following strings: SQLITE_OK,  ** SQLITE_IGNORE, or SQLITE_DENY.  Any other return value is an error.  **  ** If this method is invoked with no arguments, the current authorization  ** callback string is returned.  */  case DB_AUTHORIZER: {#ifdef SQLITE_OMIT_AUTHORIZATION    Tcl_AppendResult(interp, "authorization not available in this build", 0);    return TCL_ERROR;#else    if( objc>3 ){      Tcl_WrongNumArgs(interp, 2, objv, "?CALLBACK?");      return TCL_ERROR;    }else if( objc==2 ){      if( pDb->zAuth ){        Tcl_AppendResult(interp, pDb->zAuth, 0);      }    }else{      char *zAuth;      int len;      if( pDb->zAuth ){        Tcl_Free(pDb->zAuth);      }      zAuth = Tcl_GetStringFromObj(objv[2], &len);      if( zAuth && len>0 ){        pDb->zAuth = Tcl_Alloc( len + 1 );        memcpy(pDb->zAuth, zAuth, len+1);      }else{        pDb->zAuth = 0;      }      if( pDb->zAuth ){        pDb->interp = interp;        sqlite3_set_authorizer(pDb->db, auth_callback, pDb);      }else{        sqlite3_set_authorizer(pDb->db, 0, 0);      }    }#endif    break;  }  /*    $db busy ?CALLBACK?  **  ** Invoke the given callback if an SQL statement attempts to open  ** a locked database file.  */  case DB_BUSY: {    if( objc>3 ){      Tcl_WrongNumArgs(interp, 2, objv, "CALLBACK");      return TCL_ERROR;    }else if( objc==2 ){      if( pDb->zBusy ){        Tcl_AppendResult(interp, pDb->zBusy, 0);      }    }else{      char *zBusy;      int len;      if( pDb->zBusy ){        Tcl_Free(pDb->zBusy);      }      zBusy = Tcl_GetStringFromObj(objv[2], &len);      if( zBusy && len>0 ){        pDb->zBusy = Tcl_Alloc( len + 1 );        memcpy(pDb->zBusy, zBusy, len+1);      }else{        pDb->zBusy = 0;      }      if( pDb->zBusy ){        pDb->interp = interp;        sqlite3_busy_handler(pDb->db, DbBusyHandler, pDb);      }else{        sqlite3_busy_handler(pDb->db, 0, 0);      }    }    break;  }  /*     $db cache flush  **     $db cache size n  **  ** Flush the prepared statement cache, or set the maximum number of  ** cached statements.  */  case DB_CACHE: {    char *subCmd;    int n;    if( objc<=2 ){      Tcl_WrongNumArgs(interp, 1, objv, "cache option ?arg?");      return TCL_ERROR;    }    subCmd = Tcl_GetStringFromObj( objv[2], 0 );    if( *subCmd=='f' && strcmp(subCmd,"flush")==0 ){      if( objc!=3 ){        Tcl_WrongNumArgs(interp, 2, objv, "flush");        return TCL_ERROR;      }else{        flushStmtCache( pDb );      }    }else if( *subCmd=='s' && strcmp(subCmd,"size")==0 ){      if( objc!=4 ){        Tcl_WrongNumArgs(interp, 2, objv, "size n");        return TCL_ERROR;      }else{        if( TCL_ERROR==Tcl_GetIntFromObj(interp, objv[3], &n) ){          Tcl_AppendResult( interp, "cannot convert \"",                Tcl_GetStringFromObj(objv[3],0), "\" to integer", 0);          return TCL_ERROR;        }else{          if( n<0 ){            flushStmtCache( pDb );            n = 0;          }else if( n>MAX_PREPARED_STMTS ){            n = MAX_PREPARED_STMTS;          }          pDb->maxStmt = n;        }      }    }else{      Tcl_AppendResult( interp, "bad option \"",           Tcl_GetStringFromObj(objv[2],0), "\": must be flush or size", 0);      return TCL_ERROR;    }    break;  }  /*     $db changes  **  ** Return the number of rows that were modified, inserted, or deleted by  ** the most recent INSERT, UPDATE or DELETE statement, not including   ** any changes made by trigger programs.  */  case DB_CHANGES: {    Tcl_Obj *pResult;    if( objc!=2 ){      Tcl_WrongNumArgs(interp, 2, objv, "");      return TCL_ERROR;    }    pResult = Tcl_GetObjResult(interp);    Tcl_SetIntObj(pResult, sqlite3_changes(pDb->db));    break;  }  /*    $db close  **  ** Shutdown the database  */  case DB_CLOSE: {    Tcl_DeleteCommand(interp, Tcl_GetStringFromObj(objv[0], 0));    break;  }  /*  **     $db collate NAME SCRIPT  **  ** Create a new SQL collation function called NAME.  Whenever  ** that function is called, invoke SCRIPT to evaluate the function.  */  case DB_COLLATE: {    SqlCollate *pCollate;    char *zName;    char *zScript;    int nScript;    if( objc!=4 ){      Tcl_WrongNumArgs(interp, 2, objv, "NAME SCRIPT");      return TCL_ERROR;    }    zName = Tcl_GetStringFromObj(objv[2], 0);    zScript = Tcl_GetStringFromObj(objv[3], &nScript);    pCollate = (SqlCollate*)Tcl_Alloc( sizeof(*pCollate) + nScript + 1 );    if( pCollate==0 ) return TCL_ERROR;    pCollate->interp = interp;    pCollate->pNext = pDb->pCollate;    pCollate->zScript = (char*)&pCollate[1];    pDb->pCollate = pCollate;    memcpy(pCollate->zScript, zScript, nScript+1);    if( sqlite3_create_collation(pDb->db, zName, SQLITE_UTF8,         pCollate, tclSqlCollate) ){      Tcl_SetResult(interp, (char *)sqlite3_errmsg(pDb->db), TCL_VOLATILE);      return TCL_ERROR;    }    break;  }  /*  **     $db collation_needed SCRIPT  **  ** Create a new SQL collation function called NAME.  Whenever  ** that function is called, invoke SCRIPT to evaluate the function.  */  case DB_COLLATION_NEEDED: {    if( objc!=3 ){      Tcl_WrongNumArgs(interp, 2, objv, "SCRIPT");      return TCL_ERROR;    }    if( pDb->pCollateNeeded ){      Tcl_DecrRefCount(pDb->pCollateNeeded);    }    pDb->pCollateNeeded = Tcl_DuplicateObj(objv[2]);    Tcl_IncrRefCount(pDb->pCollateNeeded);    sqlite3_collation_needed(pDb->db, pDb, tclCollateNeeded);    break;  }  /*    $db commit_hook ?CALLBACK?  **  ** Invoke the given callback just before committing every SQL transaction.  ** If the callback throws an exception or returns non-zero, then the  ** transaction is aborted.  If CALLBACK is an empty string, the callback  ** is disabled.  */  case DB_COMMIT_HOOK: {    if( objc>3 ){      Tcl_WrongNumArgs(interp, 2, objv, "?CALLBACK?");      return TCL_ERROR;    }else if( objc==2 ){      if( pDb->zCommit ){        Tcl_AppendResult(interp, pDb->zCommit, 0);      }    }else{      char *zCommit;      int len;      if( pDb->zCommit ){        Tcl_Free(pDb->zCommit);      }      zCommit = Tcl_GetStringFromObj(objv[2], &len);      if( zCommit && len>0 ){        pDb->zCommit = Tcl_Alloc( len + 1 );        memcpy(pDb->zCommit, zCommit, len+1);      }else{        pDb->zCommit = 0;      }      if( pDb->zCommit ){        pDb->interp = interp;        sqlite3_commit_hook(pDb->db, DbCommitHandler, pDb);      }else{        sqlite3_commit_hook(pDb->db, 0, 0);      }    }    break;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -