public NativeApiContainer(INativeContext ctx) { _ctx = ctx; // Virtual member call should be fine unless we have a rogue implementer // The only implementer of this function should be SilkTouch // ReSharper disable VirtualMemberCallInConstructor _vTable = CreateVTable(); GcUtility = new GcUtility(1, CoreGcSlotCount()); PostInit(); // ReSharper restore VirtualMemberCallInConstructor }
protected NativeApiContainer(INativeContext ctx) { _ctx = ctx; // Virtual member call should be fine unless we have a rogue implementer // The only implementer of this function should be SilkTouch // ReSharper disable VirtualMemberCallInConstructor _vTable = CreateVTable(); var slotCount = CoreGetSlotCount(); if (slotCount == 0) { throw new InvalidOperationException ( "The derived class does not implement CoreGetSlotCount, or does not have any slots." + "This could be because of a SilkTouch bug, or because you're not using SilkTouch at all." ); } _vTable.Initialize(_ctx, slotCount); GcUtility = new GcUtility(1, CoreGcSlotCount()); // ReSharper restore VirtualMemberCallInConstructor }
public static RC Sync(Context ctx, ref string errorOut) { RC rc = RC.OK; VTable[] vtrans = ctx.VTrans.data; ctx.VTrans.data = null; for (int i = 0; rc == RC.OK && i < ctx.VTrans.length; i++) { Func <IVTable, int> x = null; IVTable ivtable = vtrans[i].IVTable; if (ivtable != null && (x = ivtable.IModule.Sync) != null) { rc = (RC)x(ivtable); C._tagfree(ctx, ref errorOut); errorOut = ivtable.ErrMsg; C._free(ref ivtable.ErrMsg); } } ctx.VTrans.data = vtrans; return(rc); }
static void CallFinaliser(Context ctx, int offset) { if (ctx.VTrans.data != null) { for (int i = 0; i < ctx.VTrans.length; i++) { VTable vtable = ctx.VTrans[i]; IVTable ivtable = vtable.IVTable; if (ivtable != null) { Func <IVTable, int> x = null; if (offset == 0) { x = ivtable.IModule.Rollback; } else if (offset == 1) { x = ivtable.IModule.Commit; } else { throw new InvalidOperationException(); } if (x != null) { x(ivtable); } } vtable.Savepoints = 0; vtable.Unlock(); } C._tagfree(ctx, ref ctx.VTrans.data); ctx.VTrans.length = 0; ctx.VTrans.data = null; } }
protected IVTable SwapVTable(IVTable newVTable) => Interlocked.Exchange(ref _vTable, newVTable);
static void ImportVtabErrMsg(Vdbe p, IVTable vtab) { Context db = p.Ctx; C._tagfree(db, ref p.ErrMsg); p.ErrMsg = vtab.ErrMsg; C._free(ref vtab.ErrMsg); vtab.ErrMsg = null; }
public static FuncDef OverloadFunction(Context ctx, FuncDef def, int argsLength, Expr expr) { // Check to see the left operand is a column in a virtual table if (C._NEVER(expr == null)) { return(def); } if (expr.OP != TK.COLUMN) { return(def); } Table table = expr.Table; if (C._NEVER(table == null)) { return(def); } if ((table.TabFlags & TF.Virtual) == 0) { return(def); } IVTable ivtable = GetVTable(ctx, table).IVTable; Debug.Assert(ivtable != null); Debug.Assert(ivtable.IModule != null); ITableModule imodule = (ITableModule)ivtable.IModule; if (imodule.FindFunction == null) { return(def); } // Call the xFindFunction method on the virtual table implementation to see if the implementation wants to overload this function string lowerName = def.Name; RC rc = RC.OK; Action <FuncContext, int, Mem[]> func = null; object[] args = null; if (lowerName != null) { lowerName = lowerName.ToLowerInvariant(); rc = imodule.FindFunction(ivtable, argsLength, lowerName, func, args); C._tagfree(ctx, ref lowerName); } if (rc == RC.OK) { return(def); } // Create a new ephemeral function definition for the overloaded function FuncDef newFunc = new FuncDef();//: (FuncDef*)_tagalloc(ctx, sizeof(FuncDef) + _strlen30(def->Name) + 1, true); if (newFunc == null) { return(def); } newFunc = def._memcpy(); newFunc.Name = def.Name; newFunc.Func = func; newFunc.UserData = args; newFunc.Flags |= FUNC.EPHEM; return(newFunc); }