mirror of
				https://github.com/sqlite/sqlite.git
				synced 2025-11-03 16:53:36 +03:00 
			
		
		
		
	Simplification and size reduction to the printf logic. Remove the bFlags
parameter from sqlite3VXPrintf() and sqlite3XPrintf(). Use sqlite3XPrintf() instead of sqlite3_snprintf() for rendering P4 values in EXPLAIN output. FossilOrigin-Name: 0bdb41c45aa1cc8e5c136aaa6605d54b401483bd
This commit is contained in:
		
							
								
								
									
										103
									
								
								src/vdbeaux.c
									
									
									
									
									
								
							
							
						
						
									
										103
									
								
								src/vdbeaux.c
									
									
									
									
									
								
							@@ -1117,28 +1117,27 @@ static int displayComment(
 | 
			
		||||
** Translate the P4.pExpr value for an OP_CursorHint opcode into text
 | 
			
		||||
** that can be displayed in the P4 column of EXPLAIN output.
 | 
			
		||||
*/
 | 
			
		||||
static int displayP4Expr(int nTemp, char *zTemp, Expr *pExpr){
 | 
			
		||||
static void displayP4Expr(StrAccum *p, Expr *pExpr){
 | 
			
		||||
  const char *zOp = 0;
 | 
			
		||||
  int n;
 | 
			
		||||
  switch( pExpr->op ){
 | 
			
		||||
    case TK_STRING:
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "%Q", pExpr->u.zToken);
 | 
			
		||||
      sqlite3XPrintf(p, "%Q", pExpr->u.zToken);
 | 
			
		||||
      break;
 | 
			
		||||
    case TK_INTEGER:
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "%d", pExpr->u.iValue);
 | 
			
		||||
      sqlite3XPrintf(p, "%d", pExpr->u.iValue);
 | 
			
		||||
      break;
 | 
			
		||||
    case TK_NULL:
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "NULL");
 | 
			
		||||
      sqlite3XPrintf(p, "NULL");
 | 
			
		||||
      break;
 | 
			
		||||
    case TK_REGISTER: {
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "r[%d]", pExpr->iTable);
 | 
			
		||||
      sqlite3XPrintf(p, "r[%d]", pExpr->iTable);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
    case TK_COLUMN: {
 | 
			
		||||
      if( pExpr->iColumn<0 ){
 | 
			
		||||
        sqlite3_snprintf(nTemp, zTemp, "rowid");
 | 
			
		||||
        sqlite3XPrintf(p, "rowid");
 | 
			
		||||
      }else{
 | 
			
		||||
        sqlite3_snprintf(nTemp, zTemp, "c%d", (int)pExpr->iColumn);
 | 
			
		||||
        sqlite3XPrintf(p, "c%d", (int)pExpr->iColumn);
 | 
			
		||||
      }
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
@@ -1170,21 +1169,19 @@ static int displayP4Expr(int nTemp, char *zTemp, Expr *pExpr){
 | 
			
		||||
    case TK_NOTNULL: zOp = "NOTNULL"; break;
 | 
			
		||||
 | 
			
		||||
    default:
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "%s", "expr");
 | 
			
		||||
      sqlite3XPrintf(p, "%s", "expr");
 | 
			
		||||
      break;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  if( zOp ){
 | 
			
		||||
    sqlite3_snprintf(nTemp, zTemp, "%s(", zOp);
 | 
			
		||||
    n = sqlite3Strlen30(zTemp);
 | 
			
		||||
    n += displayP4Expr(nTemp-n, zTemp+n, pExpr->pLeft);
 | 
			
		||||
    if( n<nTemp-1 && pExpr->pRight ){
 | 
			
		||||
      zTemp[n++] = ',';
 | 
			
		||||
      n += displayP4Expr(nTemp-n, zTemp+n, pExpr->pRight);
 | 
			
		||||
    sqlite3XPrintf(p, "%s(", zOp);
 | 
			
		||||
    displayP4Expr(p, pExpr->pLeft);
 | 
			
		||||
    if( pExpr->pRight ){
 | 
			
		||||
      sqlite3StrAccumAppend(p, ",", 1);
 | 
			
		||||
      displayP4Expr(p, pExpr->pRight);
 | 
			
		||||
    }
 | 
			
		||||
    sqlite3_snprintf(nTemp-n, zTemp+n, ")");
 | 
			
		||||
    sqlite3StrAccumAppend(p, ")", 1);
 | 
			
		||||
  }
 | 
			
		||||
  return sqlite3Strlen30(zTemp);
 | 
			
		||||
}
 | 
			
		||||
#endif /* VDBE_DISPLAY_P4 && defined(SQLITE_ENABLE_CURSOR_HINTS) */
 | 
			
		||||
 | 
			
		||||
@@ -1196,72 +1193,57 @@ static int displayP4Expr(int nTemp, char *zTemp, Expr *pExpr){
 | 
			
		||||
*/
 | 
			
		||||
static char *displayP4(Op *pOp, char *zTemp, int nTemp){
 | 
			
		||||
  char *zP4 = zTemp;
 | 
			
		||||
  StrAccum x;
 | 
			
		||||
  assert( nTemp>=20 );
 | 
			
		||||
  sqlite3StrAccumInit(&x, 0, zTemp, nTemp, 0);
 | 
			
		||||
  switch( pOp->p4type ){
 | 
			
		||||
    case P4_KEYINFO: {
 | 
			
		||||
      int i, j;
 | 
			
		||||
      int j;
 | 
			
		||||
      KeyInfo *pKeyInfo = pOp->p4.pKeyInfo;
 | 
			
		||||
      assert( pKeyInfo->aSortOrder!=0 );
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "k(%d", pKeyInfo->nField);
 | 
			
		||||
      i = sqlite3Strlen30(zTemp);
 | 
			
		||||
      sqlite3XPrintf(&x, "k(%d", pKeyInfo->nField);
 | 
			
		||||
      for(j=0; j<pKeyInfo->nField; j++){
 | 
			
		||||
        CollSeq *pColl = pKeyInfo->aColl[j];
 | 
			
		||||
        const char *zColl = pColl ? pColl->zName : "nil";
 | 
			
		||||
        int n = sqlite3Strlen30(zColl);
 | 
			
		||||
        if( n==6 && memcmp(zColl,"BINARY",6)==0 ){
 | 
			
		||||
          zColl = "B";
 | 
			
		||||
          n = 1;
 | 
			
		||||
        }
 | 
			
		||||
        if( i+n>nTemp-7 ){
 | 
			
		||||
          memcpy(&zTemp[i],",...",4);
 | 
			
		||||
          i += 4;
 | 
			
		||||
          break;
 | 
			
		||||
        }
 | 
			
		||||
        zTemp[i++] = ',';
 | 
			
		||||
        if( pKeyInfo->aSortOrder[j] ){
 | 
			
		||||
          zTemp[i++] = '-';
 | 
			
		||||
        }
 | 
			
		||||
        memcpy(&zTemp[i], zColl, n+1);
 | 
			
		||||
        i += n;
 | 
			
		||||
        const char *zColl = pColl ? pColl->zName : "";
 | 
			
		||||
        if( strcmp(zColl, "BINARY")==0 ) zColl = "B";
 | 
			
		||||
        sqlite3XPrintf(&x, ",%s%s", pKeyInfo->aSortOrder[j] ? "-" : "", zColl);
 | 
			
		||||
      }
 | 
			
		||||
      zTemp[i++] = ')';
 | 
			
		||||
      zTemp[i] = 0;
 | 
			
		||||
      assert( i<nTemp );
 | 
			
		||||
      sqlite3StrAccumAppend(&x, ")", 1);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
#ifdef SQLITE_ENABLE_CURSOR_HINTS
 | 
			
		||||
    case P4_EXPR: {
 | 
			
		||||
      displayP4Expr(nTemp, zTemp, pOp->p4.pExpr);
 | 
			
		||||
      displayP4Expr(&x, pOp->p4.pExpr);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
#endif
 | 
			
		||||
    case P4_COLLSEQ: {
 | 
			
		||||
      CollSeq *pColl = pOp->p4.pColl;
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "(%.20s)", pColl->zName);
 | 
			
		||||
      sqlite3XPrintf(&x, "(%.20s)", pColl->zName);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
    case P4_FUNCDEF: {
 | 
			
		||||
      FuncDef *pDef = pOp->p4.pFunc;
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "%s(%d)", pDef->zName, pDef->nArg);
 | 
			
		||||
      sqlite3XPrintf(&x, "%s(%d)", pDef->zName, pDef->nArg);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
#ifdef SQLITE_DEBUG
 | 
			
		||||
    case P4_FUNCCTX: {
 | 
			
		||||
      FuncDef *pDef = pOp->p4.pCtx->pFunc;
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "%s(%d)", pDef->zName, pDef->nArg);
 | 
			
		||||
      sqlite3XPrintf(&x, "%s(%d)", pDef->zName, pDef->nArg);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
#endif
 | 
			
		||||
    case P4_INT64: {
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "%lld", *pOp->p4.pI64);
 | 
			
		||||
      sqlite3XPrintf(&x, "%lld", *pOp->p4.pI64);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
    case P4_INT32: {
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "%d", pOp->p4.i);
 | 
			
		||||
      sqlite3XPrintf(&x, "%d", pOp->p4.i);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
    case P4_REAL: {
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "%.16g", *pOp->p4.pReal);
 | 
			
		||||
      sqlite3XPrintf(&x, "%.16g", *pOp->p4.pReal);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
    case P4_MEM: {
 | 
			
		||||
@@ -1269,11 +1251,11 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){
 | 
			
		||||
      if( pMem->flags & MEM_Str ){
 | 
			
		||||
        zP4 = pMem->z;
 | 
			
		||||
      }else if( pMem->flags & MEM_Int ){
 | 
			
		||||
        sqlite3_snprintf(nTemp, zTemp, "%lld", pMem->u.i);
 | 
			
		||||
        sqlite3XPrintf(&x, "%lld", pMem->u.i);
 | 
			
		||||
      }else if( pMem->flags & MEM_Real ){
 | 
			
		||||
        sqlite3_snprintf(nTemp, zTemp, "%.16g", pMem->u.r);
 | 
			
		||||
        sqlite3XPrintf(&x, "%.16g", pMem->u.r);
 | 
			
		||||
      }else if( pMem->flags & MEM_Null ){
 | 
			
		||||
        sqlite3_snprintf(nTemp, zTemp, "NULL");
 | 
			
		||||
        zP4 = "NULL";
 | 
			
		||||
      }else{
 | 
			
		||||
        assert( pMem->flags & MEM_Blob );
 | 
			
		||||
        zP4 = "(blob)";
 | 
			
		||||
@@ -1283,30 +1265,24 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){
 | 
			
		||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
 | 
			
		||||
    case P4_VTAB: {
 | 
			
		||||
      sqlite3_vtab *pVtab = pOp->p4.pVtab->pVtab;
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "vtab:%p", pVtab);
 | 
			
		||||
      sqlite3XPrintf(&x, "vtab:%p", pVtab);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
#endif
 | 
			
		||||
    case P4_INTARRAY: {
 | 
			
		||||
      int i, j;
 | 
			
		||||
      int i;
 | 
			
		||||
      int *ai = pOp->p4.ai;
 | 
			
		||||
      int n = ai[0];   /* The first element of an INTARRAY is always the
 | 
			
		||||
                       ** count of the number of elements to follow */
 | 
			
		||||
      for(i=1; i<n; i++){
 | 
			
		||||
        sqlite3XPrintf(&x, ",%d", ai[i]);
 | 
			
		||||
      }
 | 
			
		||||
      zTemp[0] = '[';
 | 
			
		||||
      for(i=j=1; i<n && j<nTemp-7; i++){
 | 
			
		||||
        if( j>1 ) zTemp[j++] = ',';
 | 
			
		||||
        sqlite3_snprintf(nTemp-j, zTemp+j, "%d", ai[i]);
 | 
			
		||||
        j += sqlite3Strlen30(zTemp+j);
 | 
			
		||||
      }
 | 
			
		||||
      if( i<n ){
 | 
			
		||||
        memcpy(zTemp+j, ",...]", 6);
 | 
			
		||||
      }else{
 | 
			
		||||
        memcpy(zTemp+j, "]", 2);
 | 
			
		||||
      }
 | 
			
		||||
      sqlite3StrAccumAppend(&x, "]", 1);
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
    case P4_SUBPROGRAM: {
 | 
			
		||||
      sqlite3_snprintf(nTemp, zTemp, "program");
 | 
			
		||||
      sqlite3XPrintf(&x, "program");
 | 
			
		||||
      break;
 | 
			
		||||
    }
 | 
			
		||||
    case P4_ADVANCE: {
 | 
			
		||||
@@ -1321,6 +1297,7 @@ static char *displayP4(Op *pOp, char *zTemp, int nTemp){
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
  sqlite3StrAccumFinish(&x);
 | 
			
		||||
  assert( zP4!=0 );
 | 
			
		||||
  return zP4;
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user