protected abstract IntPtr InternalGetStaticsBasePointer(StaticsBaseBlock statics_base_block);
protected override IntPtr InternalGetStaticsBasePointer(StaticsBaseBlock statics_base_block) { if (get_statics_base_pointer_func == null) { var fields = typeof(T).GetFields(BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.DeclaredOnly); FieldInfo gc_static_field_info = null; FieldInfo non_gc_static_field_info = null; FieldInfo thread_gc_static_field_info = null; FieldInfo thread_non_gc_static_field_info = null; foreach (var item in fields) { if (item.IsLiteral) { continue; } switch (TypeHelper.GetStaticBaseBlock(item)) { case StaticsBaseBlock.GC: gc_static_field_info ??= item; break; case StaticsBaseBlock.NonGC: non_gc_static_field_info ??= item; break; case StaticsBaseBlock.ThreadGC: thread_gc_static_field_info ??= item; break; case StaticsBaseBlock.ThreadNonGC: thread_non_gc_static_field_info ??= item; break; } } if (gc_static_field_info == null && non_gc_static_field_info == null && thread_gc_static_field_info == null && thread_non_gc_static_field_info == null) { return(IntPtr.Zero); } get_statics_base_pointer_func = DynamicAssembly.DefineDynamicMethod <GetStaticsBasePointerFunc>((dym, ilGen) => { if (gc_static_field_info != null) { ilGen.LoadArgument(0); ilGen.LoadFieldAddress(gc_static_field_info); ilGen.LoadConstant(TypeHelper.OffsetOf(gc_static_field_info)); ilGen.Subtract(); ilGen.StoreValue(typeof(IntPtr)); } if (non_gc_static_field_info != null) { ilGen.LoadArgument(1); ilGen.LoadFieldAddress(non_gc_static_field_info); ilGen.LoadConstant(TypeHelper.OffsetOf(non_gc_static_field_info)); ilGen.Subtract(); ilGen.StoreValue(typeof(IntPtr)); } if (thread_gc_static_field_info != null) { ilGen.LoadArgument(2); ilGen.LoadFieldAddress(thread_gc_static_field_info); ilGen.LoadConstant(TypeHelper.OffsetOf(thread_gc_static_field_info)); ilGen.Subtract(); ilGen.StoreValue(typeof(IntPtr)); } if (thread_non_gc_static_field_info != null) { ilGen.LoadArgument(3); ilGen.LoadFieldAddress(thread_non_gc_static_field_info); ilGen.LoadConstant(TypeHelper.OffsetOf(thread_non_gc_static_field_info)); ilGen.Subtract(); ilGen.StoreValue(typeof(IntPtr)); } ilGen.Return(); }, typeof(T).Module, true); } get_statics_base_pointer_func( out var gc_statics_base_pointer, out var non_gc_statics_base_pointer, out var thread_gc_statics_base_pointer, out var thread_non_gc_statics_base_pointer ); return(statics_base_block switch { StaticsBaseBlock.GC => gc_statics_base_pointer, StaticsBaseBlock.NonGC => non_gc_statics_base_pointer, StaticsBaseBlock.ThreadGC => thread_gc_statics_base_pointer, StaticsBaseBlock.ThreadNonGC => thread_non_gc_statics_base_pointer, _ => throw new NotSupportedException(), });
public static IntPtr GetStaticsBasePointer(Type type, StaticsBaseBlock statics_base_block) { return(GetOrCreate(type).InternalGetStaticsBasePointer(statics_base_block)); }