public ILEmitter Emit(ILEmitter il, Label gotoNext) { var variableType = _variable.VariableType; if (variableType.IsValueType) { _variable.LoadAddress(il, Arg.X); _variable.Load(il, Arg.Y); } else { _variable.Load(il, Arg.X).Stloc(variableType, out var x); _variable.Load(il, Arg.Y).Stloc(variableType, out var y) .Ldloc(x) .Brtrue_S(out var call) .Ldloc(y) .Brfalse_S(gotoNext) .Ret(-1) .MarkLabel(call) .Ldloc(x) .Ldloc(y); } return(il.CallMethod(_compareToMethod)); }
public ILEmitter Emit(ILEmitter il, Label _) => il.CallMethod( _equalityMethod, _variable.VariableType.IsValueType ? _variable.LoadAddress(Arg.X) : _variable.Load(Arg.X), _variable.Load(Arg.Y));
public ILEmitter Emit(ILEmitter il, Label _) => il.CallMethod( _method, LoadArgument(Arg.Context), _variable.Load(Arg.X), _variable.Load(Arg.Y), LoadArgument(Arg.SetX), LoadArgument(Arg.SetY));
private (LocalBuilder xEnumerator, LocalBuilder yEnumerator) EmitLoadEnumerators(ILEmitter il, LocalBuilder xEnumerable, LocalBuilder yEnumerable) { il.CallMethod(_getEnumeratorMethod, LoadCaller(xEnumerable)) .Stloc(_enumeratorType, out var xEnumerator) .CallMethod(_getEnumeratorMethod, LoadCaller(yEnumerable)) .Stloc(_enumeratorType, out var yEnumerator); // todo: 3. check enumerators for null? return(xEnumerator, yEnumerator); }
public ILEmitter Load(ILEmitter il, ushort arg) { if (OwnerType.IsValueType) { il.LoadArgumentAddress(arg); } else { il.LoadArgument(arg); } return(il.CallMethod(_propertyInfo.GetMethod)); }
public static ILEmitter EmitCheckNullablesForValue(this ILEmitter il, ILEmitterFunc nullableX, ILEmitterFunc nullableY, Type nullableType, Label ifBothNull) { var hasValueMethod = nullableType.GetPropertyGetter("HasValue"); return(il.CallMethod(hasValueMethod, nullableY) .Stloc(typeof(bool), out var secondHasValue) .CallMethod(hasValueMethod, nullableX) .Brtrue_S(out var ifFirstHasValue) .Ldloc(secondHasValue) .Brfalse(ifBothNull) .Ret(0) .MarkLabel(ifFirstHasValue) .Ldloc(secondHasValue) .Brtrue_S(out var next) .Ret(0) .MarkLabel(next)); }
public ILEmitter Emit(ILEmitter il, LocalBuilder hash) { il.Emit(_variable.Load(Arg.Input)) .Stloc(_variable.VariableType, out var enumerable) .DefineLabel(out var end); if (!_variable.VariableType.IsValueType) { il.Brtrue_S(Ldloc(enumerable), out var begin) .Ldc_I4(0) .Br(end) .MarkLabel(begin); } if (_configuration.Get(_variable.OwnerType).IgnoreCollectionOrder) { return(EmitHashAsSortedArray(il, enumerable, hash).MarkLabel(end)); } il.CallMethod(_getEnumeratorMethod, LoadCaller(enumerable)) .Stloc(_enumeratorType, out var enumerator) .DefineLabel(out var loopStart); if (!_enumeratorType.IsValueType) { il.Brtrue_S(Ldloc(enumerator), loopStart) .Ldc_I4(0) .Br(end); } // todo: 1. think how to use try/finally block // the problem now with the inner `return` statements, it has to be `leave` instruction //il.BeginExceptionBlock(); Loop(il, enumerator, loopStart, hash); //il.BeginFinallyBlock(); EmitDisposeEnumerator(il, enumerator); //il.EndExceptionBlock(); return(il.Ldloc(hash).MarkLabel(end)); }
public ILEmitter Emit(ILEmitter il, Label _) => il.CallMethod( _compareMethod, _variable.Load(Arg.X), _variable.Load(Arg.Y), Ldc_I4(_stringComparisonType));
public ILEmitter Emit(ILEmitter il) => il.CallMethod( _getHashMethod, _variable.VariableType.IsValueType ? _variable.LoadAddress(Arg.Input) : _variable.Load(Arg.Input));
public ILEmitter LoadAddress(ILEmitter il, ushort arg) => il .CallMethod(_getCurrentMethod, LoadCaller(_enumerators[arg])) .Stloc(VariableType, out var local) .LoadLocalAddress(local);
public ILEmitter Load(ILEmitter il, ushort arg) => il.CallMethod(_getCurrentMethod, LoadCaller(_enumerators[arg]));
public ILEmitter Load(ILEmitter il, ushort arg) => il.CallMethod( _getItemMethod, Ldloc(_arrays[arg]), Ldloc(_indexVariable));
public ILEmitter Emit(ILEmitter il, Label _) => il.CallMethod( _equalityMethod, _variable.Load(Arg.X), _variable.Load(Arg.Y));