/// <summary> /// Emit elements into an array /// </summary> private static void EmitElementArrayLoad(BaseExpressionElement[] elements, Type arrayElementType, YaleIlGenerator ilg, ExpressionContext context) { // Load the array length LiteralElement.EmitLoad(elements.Length, ilg); // Create the array ilg.Emit(OpCodes.Newarr, arrayElementType); // Store the new array in a unique local and remember the index var local = ilg.DeclareLocal(arrayElementType.MakeArrayType()); var arrayLocalIndex = local.LocalIndex; Utility.EmitStoreLocal(ilg, arrayLocalIndex); for (var i = 0; i <= elements.Length - 1; i++) { // Load the array Utility.EmitLoadLocal(ilg, arrayLocalIndex); // Load the index LiteralElement.EmitLoad(i, ilg); // Emit the element (with any required conversions) var element = elements[i]; element.Emit(ilg, context); ImplicitConverter.EmitImplicitConvert(element.ResultType, arrayElementType, ilg); // Store it into the array Utility.EmitArrayStore(ilg, arrayElementType); } // Load the array Utility.EmitLoadLocal(ilg, arrayLocalIndex); }
private void EmitListIn(YaleIlGenerator ilg, ExpressionContext context, BranchManager branchManager) { var compareElement = new CompareElement(); var endLabel = branchManager.FindLabel("endLabel"); var trueTerminal = branchManager.FindLabel("trueTerminal"); // Cache the operand since we will be comparing against it a lot var lb = ilg.DeclareLocal(operand.ResultType); var targetIndex = lb.LocalIndex; operand.Emit(ilg, context); Utility.EmitStoreLocal(ilg, targetIndex); // Wrap our operand in a local shim var targetShim = new LocalBasedElement(operand, targetIndex); // Emit the compares foreach (var argumentElement in arguments) { compareElement.Initialize(targetShim, argumentElement, LogicalCompareOperation.Equal); compareElement.Emit(ilg, context); EmitBranchToTrueTerminal(ilg, trueTerminal, branchManager); } ilg.Emit(OpCodes.Ldc_I4_0); ilg.Emit(OpCodes.Br_S, endLabel); branchManager.MarkLabel(ilg, trueTerminal); ilg.MarkLabel(trueTerminal); ilg.Emit(OpCodes.Ldc_I4_1); branchManager.MarkLabel(ilg, endLabel); ilg.MarkLabel(endLabel); }