void lsqlite3lib_xfinal_callback(sqlite3_context* ctx) { func* f = (func*)sqlite3_user_data(ctx); conn* c = f->c; int* ref = sqlite3_aggregate_context(ctx, sizeof(int)); if(!ref) sqlite3_result_error_nomem(ctx); lua_rawgeti(c->L, LUA_REGISTRYINDEX, c->ref); lua_rawgeti(c->L, -1, IDX_FUNCTION_TABLE); lua_pushstring(c->L, f->func_name); lua_rawget(c->L, -2); lua_rawgeti(c->L, -1, IDX_FUNC_XFINAL); lua_rawgeti(c->L, LUA_REGISTRYINDEX, *ref); lua_call(c->L, 1, 1); if(*ref != 0) { luaL_unref(c->L, LUA_REGISTRYINDEX, *ref); *ref = 0; } switch(lua_type(c->L, -1)) { case LUA_TBOOLEAN: sqlite3_result_int(ctx, lua_tointeger(c->L, -1)); break; case LUA_TNUMBER: if(luaL_checknumber(c->L, -1) - luaL_checklong(c->L, -1) > 0) { sqlite3_result_double(ctx, lua_tonumber(c->L, -1)); } else { sqlite3_result_int(ctx, lua_tointeger(c->L, -1)); } break; case LUA_TSTRING: { const char* ret = lua_tostring(c->L, -1); sqlite3_result_text(ctx, ret, strlen(ret), SQLITE_TRANSIENT); break; } case LUA_TNIL: default: sqlite3_result_null(ctx); break; } lua_pop(c->L, 2); }
/* ** Routines to implement the count() aggregate function. */ static void countStep(sqlite3_context *context, int argc, sqlite3_value **argv){ CountCtx *p; p = sqlite3_aggregate_context(context, sizeof(*p)); if( (argc==0 || SQLITE_NULL!=sqlite3_value_type(argv[0])) && p ){ p->n++; } #ifndef SQLITE_OMIT_DEPRECATED /* The sqlite3_aggregate_count() function is deprecated. But just to make ** sure it still operates correctly, verify that its count agrees with our ** internal count when using count(*) and when the total count can be ** expressed as a 32-bit integer. */ assert( argc==1 || p==0 || p->n>0x7fffffff || p->n==sqlite3_aggregate_count(context) ); #endif }
void lsqlite3lib_xstep_callback(sqlite3_context* ctx,int n, sqlite3_value** value) { int i; func* f = (func*)sqlite3_user_data(ctx); conn* c = f->c; int* ref = sqlite3_aggregate_context(ctx, sizeof(int)); if(!ref) sqlite3_result_error_nomem(ctx); if(*ref == 0) { lua_newtable(c->L); *ref = luaL_ref(c->L, LUA_REGISTRYINDEX); } lua_rawgeti(c->L, LUA_REGISTRYINDEX, c->ref); lua_rawgeti(c->L, -1, IDX_FUNCTION_TABLE); lua_pushstring(c->L, f->func_name); lua_rawget(c->L, -2); lua_rawgeti(c->L, -1, IDX_FUNC_XSTEP); lua_createtable(c->L, n, 0); for(i = 0; i < n; i++) { lua_pushinteger(c->L, i + 1); switch(sqlite3_value_type(*(value+i))) { case SQLITE_INTEGER: lua_pushinteger(c->L, sqlite3_value_int(*(value+i))); break; case SQLITE_FLOAT: lua_pushnumber(c->L, sqlite3_value_double(*(value+i))); break; case SQLITE3_TEXT: lua_pushstring(c->L, (const char*)sqlite3_value_text(*(value+i))); break; case SQLITE_BLOB: case SQLITE_NULL: default: lua_pushnil(c->L); break; } lua_rawset(c->L, -3); } lua_rawgeti(c->L, LUA_REGISTRYINDEX, *ref); lua_call(c->L, 2, 0); }
static void SFinalize(sqlite3_context *context){ SCtx *p=NULL; char *buf=NULL; p = (SCtx *) sqlite3_aggregate_context(context, sizeof(*p)); ss[p->sscnt] << ")"; buf = (char *) malloc (sizeof(char)*(ss[p->sscnt].str().size()+1)); if (buf == NULL) fprintf(stderr,"malloc error in SNFinalize, buf\n"); snprintf(buf,ss[p->sscnt].str().size()+1,"%s",ss[p->sscnt].str().c_str()); sqlite3_result_text(context,buf,ss[p->sscnt].str().size()+1,free ); sscnt--; }
/* ** Routines used to compute the sum */ static void SStep(sqlite3_context *context, int argc, sqlite3_value **argv){ SCtx *p=NULL; int i; std::string d; if( argc<1 ) return; p = (SCtx *) sqlite3_aggregate_context(context, sizeof(*p)); if( p->cnt == 0) { if ( sscnt >= MAXSSC ) { fprintf(stderr,"MAXSSC needs to increase\n"); exit(1); } p->sscnt=sscnt; sscnt++; ss[p->sscnt].str(""); ss[p->sscnt] << "("; d=""; } else { d=","; } p->sum += sqlite3_value_double(argv[0]); p->cnt++; ss[p->sscnt] << d << p->sum ; /* * If the simple function is not used this * comes into play. */ if (p->cnt == 1) { for(i=1; i< argc; ++i) { p->cnt++; p->sum+=sqlite3_value_double(argv[i]); ss[p->sscnt] << "," << p->sum ; } } }
extern void pg_string_agg_final(sqlite3_context *context) { STRING_AGG_CONTEXT_T *ctx; ctx = (STRING_AGG_CONTEXT_T *)sqlite3_aggregate_context(context,0); if (ctx) { if (ctx->sz == 0) { sqlite3_result_null(context); } else { // SQLite3 will free what we have allocated sqlite3_result_text(context, (char *)ctx->aggr, ctx->len, sqlite3_free); ctx->aggr = (char *)NULL; ctx->sz = 0; ctx->len = 0; } } else { sqlite3_result_null(context); } }
/* ** Implementation of a checksum() aggregate SQL function */ static void checksumStep( sqlite3_context *context, int argc, sqlite3_value **argv ){ const unsigned char *zVal; int nVal, i, j; unsigned int *a; a = (unsigned*)sqlite3_aggregate_context(context, sizeof(unsigned int)*5); if( a ){ for(i=0; i<argc; i++){ nVal = sqlite3_value_bytes(argv[i]); zVal = (const unsigned char*)sqlite3_value_text(argv[i]); if( zVal ) for(j=0; j<nVal; j++) addCharToHash(a, zVal[j]); addCharToHash(a, '|'); } addCharToHash(a, '\n'); } }
void ora_var_pop_final(sqlite3_context *context) { CONTEXT_T *ctx; ctx = (CONTEXT_T *)sqlite3_aggregate_context(context,0); if (ctx) { if (ctx->n) { if (ctx->n == 1) { sqlite3_result_int(context, 0); } else { sqlite3_result_double(context, (ctx->sum_sqr - (ctx->sum * ctx->sum)/ctx->n) / ctx->n); } } else { sqlite3_result_null(context); } } else { sqlite3_result_null(context); } }
/* ** Routines used to compute the sum, average, and total. ** ** The SUM() function follows the (broken) SQL standard which means ** that it returns NULL if it sums over no inputs. TOTAL returns ** 0.0 in that case. In addition, TOTAL always returns a float where ** SUM might return an integer if it never encounters a floating point ** value. ** ** I am told that SUM() should raise an exception if it encounters ** a integer overflow. But after pondering this, I decided that ** behavior leads to brittle programs. So instead, I have coded ** SUM() to revert to using floating point if it encounters an ** integer overflow. The answer may not be exact, but it will be ** close. If the SUM() function returns an integer, the value is ** exact. If SUM() returns a floating point value, it means the ** value might be approximated. */ static void sumStep(sqlite3_context *context, int argc, sqlite3_value **argv){ SumCtx *p; int type; assert( argc==1 ); p = sqlite3_aggregate_context(context, sizeof(*p)); type = sqlite3_value_numeric_type(argv[0]); if( p && type!=SQLITE_NULL ){ p->cnt++; if( type==SQLITE_INTEGER ){ p->sum += sqlite3_value_int64(argv[0]); if( !p->approx ){ i64 iVal; p->approx = p->sum!=(LONGDOUBLE_TYPE)(iVal = (i64)p->sum); } }else{ p->sum += sqlite3_value_double(argv[0]); p->approx = 1; } } }
/* ** Routines used to compute the sum, average, and total. ** ** The SUM() function follows the (broken) SQL standard which means ** that it returns NULL if it sums over no inputs. TOTAL returns ** 0.0 in that case. In addition, TOTAL always returns a float where ** SUM might return an integer if it never encounters a floating point ** value. TOTAL never fails, but SUM might through an exception if ** it overflows an integer. */ static void sumStep(sqlite3_context *context, int argc, sqlite3_value **argv){ SumCtx *p; int type; assert( argc==1 ); UNUSED_PARAMETER(argc); p = sqlite3_aggregate_context(context, sizeof(*p)); type = sqlite3_value_numeric_type(argv[0]); if( p && type!=SQLITE_NULL ){ p->cnt++; if( type==SQLITE_INTEGER ){ i64 v = sqlite3_value_int64(argv[0]); p->rSum += v; if( (p->approx|p->overflow)==0 && sqlite3AddInt64(&p->iSum, v) ){ p->overflow = 1; } }else{ p->rSum += sqlite3_value_double(argv[0]); p->approx = 1; } } }
static void listStep(sqlite3_context *context, int argc, sqlite3_value **argv){ Ltx *p; int i; std::string d=""; if( argc<1 ) return; p = (Ltx *) sqlite3_aggregate_context(context, sizeof(*p)); if ( p->cnt == 0) { if (sscntL >= MAXSSL ) { fprintf(stderr,"Above in listStep increase MAXSSL size\n"); exit(1); } p->sscnt=sscntL; sscntL++; ssL[p->sscnt].str(""); ssL[p->sscnt] << "("; } else { d=","; } p->cnt++; //ssL[p->sscnt] << "(" << p->cnt<< "," << sqlite3_value_text(argv[0]) << ")"; ssL[p->sscnt] << d << sqlite3_value_text(argv[0]); d=","; if (p->cnt == 1) { for(i=1; i< argc; ++i) { p->cnt++; ssL[p->sscnt] << d << sqlite3_value_text(argv[i]) ; } } }
extern void my_var_step(sqlite3_context *context, int argc, sqlite3_value **argv) { CONTEXT_T *ctx; int typ; double val; if ((typ = sqlite3_value_type(argv[0])) != SQLITE_NULL) { ctx = (CONTEXT_T *)sqlite3_aggregate_context(context, sizeof(CONTEXT_T)); val = my_value_double(argv[0], (double)0); if (ctx) { if (ctx->n == 0) { ctx->K = val; } ctx->sum += (val - ctx->K); ctx->sum_sqr += (val - ctx->K) * (val - ctx->K); (ctx->n)++; } } }
static void sqlite_callback_step(sqlite3_context *ctx, int argc, sqlite3_value **argv) { RefNode *klass = (RefNode*)sqlite3_user_data(ctx); Value *v = sqlite3_aggregate_context(ctx, sizeof(Value)); if (*v == VALUE_NULL) { if (!sqlite_aggrigate_new(v, klass)) { goto ERROR_END; } } fs->Value_push("v", v); sqlite_callback_args(argc, argv); if (!fs->call_member_func(fs->intern("step", -1), argc, TRUE)) { goto ERROR_END; } fs->Value_pop(); return; ERROR_END: sqlite3_result_error_code(ctx, SQLITE_ERROR_USER); return; }
static void sqlite3_do_callback(sqlite3_context *context, const Variant& callback, int argc, sqlite3_value **argv, bool is_agg) { Array params = Array::Create(); php_sqlite3_agg_context *agg_context = nullptr; if (is_agg) { agg_context = (php_sqlite3_agg_context *)sqlite3_aggregate_context (context, sizeof(php_sqlite3_agg_context)); params.appendRef(agg_context->context); params.append(agg_context->row_count); } for (int i = 0; i < argc; i++) { params.append(get_value(argv[i])); } Variant ret = vm_call_user_func(callback, params); if (!is_agg || !argv) { /* only set the sqlite return value if we are a scalar function, * or if we are finalizing an aggregate */ if (ret.isInteger()) { sqlite3_result_int(context, ret.toInt64()); } else if (ret.isNull()) { sqlite3_result_null(context); } else if (ret.isDouble()) { sqlite3_result_double(context, ret.toDouble()); } else { String sret = ret.toString(); sqlite3_result_text(context, sret.data(), sret.size(), SQLITE_TRANSIENT); } } else { /* we're stepping in an aggregate; the return value goes into * the context */ agg_context->context = ret; } }
__declspec(dllexport) void * WINAPI sqlite3_aggregate_context_interop(sqlite3_context *pctx, int n) { return sqlite3_aggregate_context(pctx, n); }
static void totalFinalize(sqlite3_context *context){ SumCtx *p; p = sqlite3_aggregate_context(context, 0); sqlite3_result_double(context, p ? p->sum : 0.0); }
int result; if ((result = strcmp(a->order, b->order)) != 0) { // Ascending return result; } else { // Descending return b->value - a->value; } } void bcsum_step(sqlite3_context *context, int argc, sqlite3_value **argv) { BCSumNode* head, * new, * curr, * prev; int t1, t2; head = (BCSumNode*)sqlite3_aggregate_context(context, sizeof(*head)); t1 = sqlite3_value_numeric_type(argv[0]); t2 = sqlite3_value_type(argv[1]); if (t1 != SQLITE_NULL && t2 != SQLITE_NULL) { new = malloc(sizeof(*new)); new->value = sqlite3_value_int(argv[0]); new->order = strdup((char*)sqlite3_value_text(argv[1])); new->next = NULL; // Insert the node in the right order if (head->next == NULL) { head->next = new; } else { prev = head; curr = prev->next;
static void countFinalize(sqlite3_context *context){ CountCtx *p; p = sqlite3_aggregate_context(context, 0); sqlite3_result_int64(context, p ? p->n : 0); }
static void int_finalize(sqlite3_context * ctx) { int64_t * val = sqlite3_aggregate_context(ctx, 0); sqlite3_result_int64(ctx, val? *val: 0); }
static void totalFinalize(sqlite3_context *context){ SumCtx *p; p = sqlite3_aggregate_context(context, 0); /* (double)0 In case of SQLITE_OMIT_FLOATING_POINT... */ sqlite3_result_double(context, p ? p->rSum : (double)0); }
static int do_callback(struct pdo_sqlite_fci *fc, zval *cb, int argc, sqlite3_value **argv, sqlite3_context *context, int is_agg) { zval *zargs = NULL; zval retval; int i; int ret; int fake_argc; zend_reference *agg_context = NULL; if (is_agg) { is_agg = 2; } fake_argc = argc + is_agg; fc->fci.size = sizeof(fc->fci); ZVAL_COPY_VALUE(&fc->fci.function_name, cb); fc->fci.object = NULL; fc->fci.retval = &retval; fc->fci.param_count = fake_argc; /* build up the params */ if (fake_argc) { zargs = safe_emalloc(fake_argc, sizeof(zval), 0); } if (is_agg) { agg_context = (zend_reference*)sqlite3_aggregate_context(context, sizeof(zend_reference)); if (!agg_context) { ZVAL_NULL(&zargs[0]); } else { if (Z_ISUNDEF(agg_context->val)) { GC_REFCOUNT(agg_context) = 1; GC_TYPE_INFO(agg_context) = IS_REFERENCE; ZVAL_NULL(&agg_context->val); } ZVAL_REF(&zargs[0], agg_context); } ZVAL_LONG(&zargs[1], sqlite3_aggregate_count(context)); } for (i = 0; i < argc; i++) { /* get the value */ switch (sqlite3_value_type(argv[i])) { case SQLITE_INTEGER: ZVAL_LONG(&zargs[i + is_agg], sqlite3_value_int(argv[i])); break; case SQLITE_FLOAT: ZVAL_DOUBLE(&zargs[i + is_agg], sqlite3_value_double(argv[i])); break; case SQLITE_NULL: ZVAL_NULL(&zargs[i + is_agg]); break; case SQLITE_BLOB: case SQLITE3_TEXT: default: ZVAL_STRINGL(&zargs[i + is_agg], (char*)sqlite3_value_text(argv[i]), sqlite3_value_bytes(argv[i])); break; } } fc->fci.params = zargs; if ((ret = zend_call_function(&fc->fci, &fc->fcc)) == FAILURE) { php_error_docref(NULL, E_WARNING, "An error occurred while invoking the callback"); } /* clean up the params */ if (zargs) { for (i = is_agg; i < fake_argc; i++) { zval_ptr_dtor(&zargs[i]); } if (is_agg) { zval_ptr_dtor(&zargs[1]); } efree(zargs); } if (!is_agg || !argv) { /* only set the sqlite return value if we are a scalar function, * or if we are finalizing an aggregate */ if (!Z_ISUNDEF(retval)) { switch (Z_TYPE(retval)) { case IS_LONG: sqlite3_result_int(context, Z_LVAL(retval)); break; case IS_NULL: sqlite3_result_null(context); break; case IS_DOUBLE: sqlite3_result_double(context, Z_DVAL(retval)); break; default: convert_to_string_ex(&retval); sqlite3_result_text(context, Z_STRVAL(retval), Z_STRLEN(retval), SQLITE_TRANSIENT); break; } } else { sqlite3_result_error(context, "failed to invoke callback", 0); } if (agg_context) { zval_ptr_dtor(&agg_context->val); } } else { /* we're stepping in an aggregate; the return value goes into * the context */ if (agg_context) { zval_ptr_dtor(&agg_context->val); } if (!Z_ISUNDEF(retval)) { ZVAL_COPY_VALUE(&agg_context->val, &retval); ZVAL_UNDEF(&retval); } else { ZVAL_UNDEF(&agg_context->val); } } if (!Z_ISUNDEF(retval)) { zval_ptr_dtor(&retval); } return ret; }
void* context::aggregate_context(int bytes) { return sqlite3_aggregate_context(handle, bytes); }
extern void pg_json_object_agg_step(sqlite3_context *context, int argc, sqlite3_value **argv) { STRING_AGG_CONTEXT_T *ctx; char *k; char *v; int len; int typ; int i; for (i = 0; i < argc; i++) { typ = sqlite3_value_type(argv[i]); if (typ == SQLITE_NULL) { return; } if (typ == SQLITE_BLOB) { ksu_err_msg(context, KSU_ERR_INV_DATATYPE, "json_agg"); return; } } k = (char *)sqlite3_value_text(argv[0]); v = (char *)sqlite3_value_text(argv[1]); len = strlen(k) + strlen(v) + 7; ctx = (STRING_AGG_CONTEXT_T *)sqlite3_aggregate_context(context, sizeof(STRING_AGG_CONTEXT_T)); if (ctx) { if (ctx->sz == 0) { if ((ctx->aggr = (char *)sqlite3_malloc((1+(len+1)/CHUNK)*CHUNK)) == (char *)NULL) { sqlite3_result_error_nomem(context); return; } ctx->sz = (1 + (len+1)/CHUNK) * CHUNK; strcpy(ctx->aggr, "{\""); strcat(ctx->aggr, k); strcat(ctx->aggr, "\":"); if ((typ == SQLITE_INTEGER) || (typ == SQLITE_FLOAT)) { strcat(ctx->aggr, v); } else { strcat(ctx->aggr, "\""); strcat(ctx->aggr, v); strcat(ctx->aggr, "\""); } ctx->len = strlen(ctx->aggr); } else { if ((ctx->len + 1 + len) > ctx->sz) { if ((ctx->aggr = (char *)sqlite3_realloc(ctx->aggr, ctx->sz + (1 + (len+1)/CHUNK) * CHUNK)) == (char *)NULL) { sqlite3_result_error_nomem(context); return; } ctx->sz += (1 + (len+1)/CHUNK) * CHUNK; } memcpy(&(ctx->aggr[ctx->len]), ",\"", 2); ctx->len += 2; len = strlen(k); memcpy(&(ctx->aggr[ctx->len]), k, len); ctx->len += len; memcpy(&(ctx->aggr[ctx->len]), "\":", 2); ctx->len += 2; if ((typ != SQLITE_INTEGER) && (typ != SQLITE_FLOAT)) { ctx->aggr[ctx->len] = '"'; (ctx->len)++; } len = strlen(v); memcpy(&(ctx->aggr[ctx->len]), v, len); ctx->len += len; if ((typ != SQLITE_INTEGER) && (typ != SQLITE_FLOAT)) { ctx->aggr[ctx->len] = '"'; (ctx->len)++; } ctx->aggr[ctx->len] = '\0'; } } }
static void sumFinalize(sqlite3_context *context){ SumCtx *p; p = sqlite3_aggregate_context(context, sizeof(*p)); sqlite3_result_double(context, p ? p->sum : 0.0); }
void* context::aggregate_data(int size) { return sqlite3_aggregate_context(ctx_, size); }