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

📄 vdbe.c

📁 SQLite 2.8.6 源代码,用来在Linux/Unix/Windows上编译安装.它是一个小型的数据库,但是非常好用,速度也快,一般的数据库查询之类的操作据统计比MySQL,PostgreSQL
💻 C
📖 第 1 页 / 共 5 页
字号:
  if( x<0 && (-x)<=p->nLabel && p->aOp ){    if( p->aLabel[-1-x]==p->nOp ) return;    assert( p->aLabel[-1-x]<0 );    p->aLabel[-1-x] = p->nOp;    for(j=0; j<p->nOp; j++){      if( p->aOp[j].p2==x ) p->aOp[j].p2 = p->nOp;    }  }}/*** Return the address of the next instruction to be inserted.*/int sqliteVdbeCurrentAddr(Vdbe *p){  assert( p->magic==VDBE_MAGIC_INIT );  return p->nOp;}/*** Add a whole list of operations to the operation stack.  Return the** address of the first operation added.*/int sqliteVdbeAddOpList(Vdbe *p, int nOp, VdbeOp const *aOp){  int addr;  assert( p->magic==VDBE_MAGIC_INIT );  if( p->nOp + nOp >= p->nOpAlloc ){    int oldSize = p->nOpAlloc;    Op *aNew;    p->nOpAlloc = p->nOpAlloc*2 + nOp + 10;    aNew = sqliteRealloc(p->aOp, p->nOpAlloc*sizeof(Op));    if( aNew==0 ){      p->nOpAlloc = oldSize;      return 0;    }    p->aOp = aNew;    memset(&p->aOp[oldSize], 0, (p->nOpAlloc-oldSize)*sizeof(Op));  }  addr = p->nOp;  if( nOp>0 ){    int i;    for(i=0; i<nOp; i++){      int p2 = aOp[i].p2;      p->aOp[i+addr] = aOp[i];      if( p2<0 ) p->aOp[i+addr].p2 = addr + ADDR(p2);      p->aOp[i+addr].p3type = aOp[i].p3 ? P3_STATIC : P3_NOTUSED;#ifndef NDEBUG      if( sqlite_vdbe_addop_trace ) vdbePrintOp(0, i+addr, &p->aOp[i+addr]);#endif    }    p->nOp += nOp;  }  return addr;}/*** Change the value of the P1 operand for a specific instruction.** This routine is useful when a large program is loaded from a** static array using sqliteVdbeAddOpList but we want to make a** few minor changes to the program.*/void sqliteVdbeChangeP1(Vdbe *p, int addr, int val){  assert( p->magic==VDBE_MAGIC_INIT );  if( p && addr>=0 && p->nOp>addr && p->aOp ){    p->aOp[addr].p1 = val;  }}/*** Change the value of the P2 operand for a specific instruction.** This routine is useful for setting a jump destination.*/void sqliteVdbeChangeP2(Vdbe *p, int addr, int val){  assert( val>=0 );  assert( p->magic==VDBE_MAGIC_INIT );  if( p && addr>=0 && p->nOp>addr && p->aOp ){    p->aOp[addr].p2 = val;  }}/*** Change the value of the P3 operand for a specific instruction.** This routine is useful when a large program is loaded from a** static array using sqliteVdbeAddOpList but we want to make a** few minor changes to the program.**** If n>=0 then the P3 operand is dynamic, meaning that a copy of** the string is made into memory obtained from sqliteMalloc().** A value of n==0 means copy bytes of zP3 up to and including the** first null byte.  If n>0 then copy n+1 bytes of zP3.**** If n==P3_STATIC  it means that zP3 is a pointer to a constant static** string and we can just copy the pointer.  n==P3_POINTER means zP3 is** a pointer to some object other than a string.**** If addr<0 then change P3 on the most recently inserted instruction.*/void sqliteVdbeChangeP3(Vdbe *p, int addr, const char *zP3, int n){  Op *pOp;  assert( p->magic==VDBE_MAGIC_INIT );  if( p==0 || p->aOp==0 ) return;  if( addr<0 || addr>=p->nOp ){    addr = p->nOp - 1;    if( addr<0 ) return;  }  pOp = &p->aOp[addr];  if( pOp->p3 && pOp->p3type==P3_DYNAMIC ){    sqliteFree(pOp->p3);    pOp->p3 = 0;  }  if( zP3==0 ){    pOp->p3 = 0;    pOp->p3type = P3_NOTUSED;  }else if( n<0 ){    pOp->p3 = (char*)zP3;    pOp->p3type = n;  }else{    sqliteSetNString(&pOp->p3, zP3, n, 0);    pOp->p3type = P3_DYNAMIC;  }}/*** If the P3 operand to the specified instruction appears** to be a quoted string token, then this procedure removes ** the quotes.**** The quoting operator can be either a grave ascent (ASCII 0x27)** or a double quote character (ASCII 0x22).  Two quotes in a row** resolve to be a single actual quote character within the string.*/void sqliteVdbeDequoteP3(Vdbe *p, int addr){  Op *pOp;  assert( p->magic==VDBE_MAGIC_INIT );  if( p->aOp==0 || addr<0 || addr>=p->nOp ) return;  pOp = &p->aOp[addr];  if( pOp->p3==0 || pOp->p3[0]==0 ) return;  if( pOp->p3type==P3_POINTER ) return;  if( pOp->p3type!=P3_DYNAMIC ){    pOp->p3 = sqliteStrDup(pOp->p3);    pOp->p3type = P3_DYNAMIC;  }  sqliteDequote(pOp->p3);}/*** On the P3 argument of the given instruction, change all** strings of whitespace characters into a single space and** delete leading and trailing whitespace.*/void sqliteVdbeCompressSpace(Vdbe *p, int addr){  char *z;  int i, j;  Op *pOp;  assert( p->magic==VDBE_MAGIC_INIT );  if( p->aOp==0 || addr<0 || addr>=p->nOp ) return;  pOp = &p->aOp[addr];  if( pOp->p3type==P3_POINTER ){    return;  }  if( pOp->p3type!=P3_DYNAMIC ){    pOp->p3 = sqliteStrDup(pOp->p3);    pOp->p3type = P3_DYNAMIC;  }  z = pOp->p3;  if( z==0 ) return;  i = j = 0;  while( isspace(z[i]) ){ i++; }  while( z[i] ){    if( isspace(z[i]) ){      z[j++] = ' ';      while( isspace(z[++i]) ){}    }else{      z[j++] = z[i++];    }  }  while( j>0 && isspace(z[j-1]) ){ j--; }  z[j] = 0;}/*** Search for the current program for the given opcode and P2** value.  Return the address plus 1 if found and 0 if not found.*/int sqliteVdbeFindOp(Vdbe *p, int op, int p2){  int i;  assert( p->magic==VDBE_MAGIC_INIT );  for(i=0; i<p->nOp; i++){    if( p->aOp[i].opcode==op && p->aOp[i].p2==p2 ) return i+1;  }  return 0;}/*** Return the opcode for a given address.*/VdbeOp *sqliteVdbeGetOp(Vdbe *p, int addr){  assert( p->magic==VDBE_MAGIC_INIT );  assert( addr>=0 && addr<p->nOp );  return &p->aOp[addr];}/*** The following group or routines are employed by installable functions** to return their results.**** The sqlite_set_result_string() routine can be used to return a string** value or to return a NULL.  To return a NULL, pass in NULL for zResult.** A copy is made of the string before this routine returns so it is safe** to pass in an ephemeral string.**** sqlite_set_result_error() works like sqlite_set_result_string() except** that it signals a fatal error.  The string argument, if any, is the** error message.  If the argument is NULL a generic substitute error message** is used.**** The sqlite_set_result_int() and sqlite_set_result_double() set the return** value of the user function to an integer or a double.**** These routines are defined here in vdbe.c because they depend on knowing** the internals of the sqlite_func structure which is only defined in ** this source file.*/char *sqlite_set_result_string(sqlite_func *p, const char *zResult, int n){  assert( !p->isStep );  if( p->s.flags & STK_Dyn ){    sqliteFree(p->z);  }  if( zResult==0 ){    p->s.flags = STK_Null;    n = 0;    p->z = 0;    p->s.n = 0;  }else{    if( n<0 ) n = strlen(zResult);    if( n<NBFS-1 ){      memcpy(p->s.z, zResult, n);      p->s.z[n] = 0;      p->s.flags = STK_Str;      p->z = p->s.z;    }else{      p->z = sqliteMallocRaw( n+1 );      if( p->z ){        memcpy(p->z, zResult, n);        p->z[n] = 0;      }      p->s.flags = STK_Str | STK_Dyn;    }    p->s.n = n+1;  }  return p->z;}void sqlite_set_result_int(sqlite_func *p, int iResult){  assert( !p->isStep );  if( p->s.flags & STK_Dyn ){    sqliteFree(p->z);  }  p->s.i = iResult;  p->s.flags = STK_Int;}void sqlite_set_result_double(sqlite_func *p, double rResult){  assert( !p->isStep );  if( p->s.flags & STK_Dyn ){    sqliteFree(p->z);  }  p->s.r = rResult;  p->s.flags = STK_Real;}void sqlite_set_result_error(sqlite_func *p, const char *zMsg, int n){  assert( !p->isStep );  sqlite_set_result_string(p, zMsg, n);  p->isError = 1;}/*** Extract the user data from a sqlite_func structure and return a** pointer to it.**** This routine is defined here in vdbe.c because it depends on knowing** the internals of the sqlite_func structure which is only defined in ** this source file.*/void *sqlite_user_data(sqlite_func *p){  assert( p && p->pFunc );  return p->pFunc->pUserData;}/*** Allocate or return the aggregate context for a user function.  A new** context is allocated on the first call.  Subsequent calls return the** same context that was returned on prior calls.**** This routine is defined here in vdbe.c because it depends on knowing** the internals of the sqlite_func structure which is only defined in** this source file.*/void *sqlite_aggregate_context(sqlite_func *p, int nByte){  assert( p && p->pFunc && p->pFunc->xStep );  if( p->pAgg==0 ){    if( nByte<=NBFS ){      p->pAgg = (void*)p->z;    }else{      p->pAgg = sqliteMalloc( nByte );    }  }  return p->pAgg;}/*** Return the number of times the Step function of a aggregate has been ** called.**** This routine is defined here in vdbe.c because it depends on knowing** the internals of the sqlite_func structure which is only defined in** this source file.*/int sqlite_aggregate_count(sqlite_func *p){  assert( p && p->pFunc && p->pFunc->xStep );  return p->cnt;}/*** Advance the virtual machine to the next output row.**** The return vale will be either SQLITE_BUSY, SQLITE_DONE, ** SQLITE_ROW, SQLITE_ERROR, or SQLITE_MISUSE.**** SQLITE_BUSY means that the virtual machine attempted to open** a locked database and there is no busy callback registered.** Call sqlite_step() again to retry the open.  *pN is set to 0** and *pazColName and *pazValue are both set to NULL.**** SQLITE_DONE means that the virtual machine has finished** executing.  sqlite_step() should not be called again on this** virtual machine.  *pN and *pazColName are set appropriately** but *pazValue is set to NULL.**** SQLITE_ROW means that the virtual machine has generated another** row of the result set.  *pN is set to the number of columns in** the row.  *pazColName is set to the names of the columns followed** by the column datatypes.  *pazValue is set to the values of each** column in the row.  The value of the i-th column is (*pazValue)[i].** The name of the i-th column is (*pazColName)[i] and the datatype** of the i-th column is (*pazColName)[i+*pN].**** SQLITE_ERROR means that a run-time error (such as a constraint** violation) has occurred.  The details of the error will be returned** by the next call to sqlite_finalize().  sqlite_step() should not** be called again on the VM.**** SQLITE_MISUSE means that the this routine was called inappropriately.** Perhaps it was called on a virtual machine that had already been** finalized or on one that had previously returned SQLITE_ERROR or** SQLITE_DONE.  Or it could be the case the the same database connection** is being used simulataneously by two or more threads.*/int sqlite_step(  sqlite_vm *pVm,              /* The virtual machine to execute */  int *pN,                     /* OUT: Number of columns in result */  const char ***pazValue,      /* OUT: Column data */  const char ***pazColName     /* OUT: Column names and datatypes */){  Vdbe *p = (Vdbe*)pVm;  sqlite *db;  int rc;  if( p->magic!=VDBE_MAGIC_RUN ){    return SQLITE_MISUSE;  }  db = p->db;  if( sqliteSafetyOn(db) ){    return SQLITE_MISUSE;  }  if( p->explain ){    rc = sqliteVdbeList(p);  }else{    rc = sqliteVdbeExec(p);  }  if( rc==SQLITE_DONE || rc==SQLITE_ROW ){    if( pazColName ) *pazColName = (const char**)p->azColName;    if( pN ) *pN = p->nResColumn;  }else{    if( pazColName) *pazColName = 0;    if( pN ) *pN = 0;  }  if( pazValue ){    if( rc==SQLITE_ROW ){      *pazValue = (const char**)p->azResColumn;    }else{      *pazValue = 0;    }  }  if( sqliteSafetyOff(db) ){    return SQLITE_MISUSE;  }  return rc;}/*** Reset an Agg structure.  Delete all its contents. **** For installable aggregate functions, if the step function has been** called, make sure the finalizer function has also been called.  The** finalizer might need to free memory that was allocated as part of its** private context.  If the finalizer has not been called yet, call it** now.*/static void AggReset(Agg *pAgg){  int i;  HashElem *p;  for(p = sqliteHashFirst(&pAgg->hash); p; p = sqliteHashNext(p)){    AggElem *pElem = sqliteHashData(p);    assert( pAgg->apFunc!=0 );    for(i=0; i<pAgg->nMem; i++){      Mem *pMem = &pElem->aMem[i];      if( pAgg->apFunc[i] && (pMem->s.flags & STK_AggCtx)!=0 ){        sqlite_func ctx;        ctx.pFunc = pAgg->apFunc[i];        ctx.s.flags = STK_Null;        ctx.z = 0;        ctx.pAgg = pMem->z;        ctx.cnt = pMem->s.i;        ctx.isStep = 0;        ctx.isError = 0;        (*pAgg->apFunc[i]->xFinalize)(&ctx);        if( pMem->z!=0 && pMem->z!=pMem->s.z ){          sqliteFree(pMem->z);        }      }else if( pMem->s.flags & STK_Dyn ){        sqliteFree(pMem->z);      }    }    sqliteFree(pElem);  }  sqliteHashClear(&pAgg->hash);

⌨️ 快捷键说明

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