internal ForCSharpStatement(ReadOnlyCollection<ParameterExpression> variables, ReadOnlyCollection<Expression> initializers, Expression test, ReadOnlyCollection<Expression> iterators, Expression body, LabelTarget breakLabel, LabelTarget continueLabel) : base(test, body, breakLabel, continueLabel) { Variables = variables; Initializers = initializers; Iterators = iterators; }
public Expression Update(LabelTarget label, Type type) { if (LabelTarget.Equals(label) && Type.Equals(type)) { return this; } return AstExpression.Continue(_continueStatement, this as IScope, Visitor); }
public override void BeforeVisit(Function node) { base.BeforeVisit(node); //_currentOutputExp = Expression.Parameter(typeof (TextWriter), CurrentOutputIdentifier); //Create return target _returnLabelTarget = Expression.Label(typeof(object), "lambdaReturn"); }
internal DoWhileExpression (Expression test, Expression body, LabelTarget breakTarget, LabelTarget continueTarget) { this.test = test; this.body = body; this.break_target = breakTarget; this.continue_target = continueTarget; }
public override Expression Compile(ParameterExpression stateParameterExpression, LabelTarget returnTarget) { return Expression.IfThenElse( Expression.Convert(this.Condition.Compile(stateParameterExpression, returnTarget), typeof(bool)), this.Statement.Compile(stateParameterExpression, returnTarget), this.ElseStatement.Compile(stateParameterExpression, returnTarget)); }
public DoWhileExpression Update (Expression test, Expression body, LabelTarget breakTarget, LabelTarget continueTarget) { if (this.test == test && this.body == body && this.break_target == breakTarget && this.continue_target == continueTarget) return this; return CustomExpression.DoWhile (test, body, breakTarget, continueTarget); }
public Expression Update(LabelTarget labelTarget, Type type) { if (LabelTarget.Equals(labelTarget) && Type.Equals(type)) { return this; } return AstExpression.Goto(_gotoStatement, this as IScope, Visitor); }
public static SwitchExpression Switch(Expression value, LabelTarget label, IEnumerable<SwitchCase> cases) { RequiresCanRead(value, "value"); ContractUtils.Requires(value.Type == typeof(int), "value", Strings.ValueMustBeInt); ContractUtils.RequiresNotNull(cases, "cases"); var caseList = cases.ToReadOnly(); ContractUtils.RequiresNotEmpty(caseList, "cases"); ContractUtils.RequiresNotNullItems(caseList, "cases"); // TODO: does it make sense for switch to have non-void type? ContractUtils.Requires(label == null || label.Type == typeof(void), "label", Strings.LabelTypeMustBeVoid); bool @default = false; int max = Int32.MinValue; int min = Int32.MaxValue; foreach (SwitchCase sc in caseList) { if (sc.IsDefault) { ContractUtils.Requires(@default == false, "cases", Strings.OnlyDefaultIsAllowed); @default = true; } else { int val = sc.Value; if (val > max) max = val; if (val < min) min = val; } } ContractUtils.Requires(UniqueCaseValues(caseList, min, max), "cases", Strings.CaseValuesMustBeUnique); return new SwitchExpression(value, label, caseList); }
public sealed override Expression Bind(object[] args, ReadOnlyCollection<ParameterExpression> parameters, LabelTarget returnLabel) { if (args.Length == 0) { throw new InvalidOperationException(); } MetaObject[] mos; if (args.Length != 1) { mos = new MetaObject[args.Length - 1]; for (int i = 1; i < args.Length; i++) { mos[i - 1] = MetaObject.ObjectToMetaObject(args[i], parameters[i]); } } else { mos = MetaObject.EmptyMetaObjects; } MetaObject binding = Bind( MetaObject.ObjectToMetaObject(args[0], parameters[0]), mos ); if (binding == null) { throw Error.BindingCannotBeNull(); } return GetMetaObjectRule(binding, returnLabel); }
public Expression Update(LabelTarget target, Expression defaultValue) { if (Target.Equals(target) && DefaultValue == defaultValue) { return this; } return AstExpression.Label(_caseLabel, ParentScope, Visitor); }
public Expression Update(GotoExpressionKind kind, LabelTarget target, Expression value) { if (Target.Equals(target) && ReferenceEquals(Value, value) && Kind == kind) { return this; } return AstExpression.Return(_returnStatement, ParentScope, Visitor); }
public Expression Update(LabelTarget labelTarget, Type type) { if (LabelTarget.Equals(labelTarget) && Type.Equals(type)) { return this; } return AstExpression.Label(_labelStatement, ParentScope, Visitor); }
internal SwitchCSharpStatement(Expression switchValue, LabelTarget breakLabel, ReadOnlyCollection<ParameterExpression> variables, ReadOnlyCollection<CSharpSwitchCase> cases) { SwitchValue = switchValue; BreakLabel = breakLabel; Variables = variables; Cases = cases; }
// Just splat the args and dispatch through a nested site public override Expression Bind(object[] args, ReadOnlyCollection<ParameterExpression> parameters, LabelTarget returnLabel) { Debug.Assert(args.Length == 2); int count = ((object[])args[1]).Length; ParameterExpression array = parameters[1]; var nestedArgs = new ReadOnlyCollectionBuilder<Expression>(count + 1); var delegateArgs = new Type[count + 3]; // args + target + returnType + CallSite nestedArgs.Add(parameters[0]); delegateArgs[0] = typeof(CallSite); delegateArgs[1] = typeof(object); for (int i = 0; i < count; i++) { nestedArgs.Add(Expression.ArrayAccess(array, Expression.Constant(i))); delegateArgs[i + 2] = typeof(object).MakeByRefType(); } delegateArgs[delegateArgs.Length - 1] = typeof(object); return Expression.IfThen( Expression.Equal(Expression.ArrayLength(array), Expression.Constant(count)), Expression.Return( returnLabel, Expression.MakeDynamic( Expression.GetDelegateType(delegateArgs), new ComInvokeAction(new CallInfo(count)), nestedArgs ) ) ); }
internal SwitchExpression(Expression testValue, LabelTarget label, ReadOnlyCollection<SwitchCase> cases) { Assert.NotNullItems(cases); _label = label; _testValue = testValue; _cases = cases; }
public ComplexFunctionBuilder(Type targetType) { _targetType = targetType; _delegateType = typeof(Combine<>).MakeGenericType(_targetType); _pCombiner = Expression.Parameter(typeof(ICombiner)); _pPrev = Expression.Parameter(_targetType); _pNext = Expression.Parameter(_targetType); _vResult = Expression.Variable(_targetType); _lbReturn = Expression.Label(_targetType); if (!_targetType.IsValueType) { _bodyList.Add(Expression.IfThen(Expression.Equal(_pNext, Expression.Constant(null)), Expression.Return(_lbReturn, _pPrev))); _bodyList.Add(Expression.IfThen(Expression.Equal(_pPrev, Expression.Constant(null)), Expression.Return(_lbReturn, _pNext))); } var ci = _targetType.GetConstructors(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic).FirstOrDefault(_ => _.GetParameters().Length == 0); Expression resultInstance; if (ci == null) { resultInstance = Expression.Call(typeof(FormatterServices).GetMethod("GetUninitializedObject"), Expression.Constant(_targetType)); resultInstance = Expression.Convert(resultInstance, _targetType); } else resultInstance = Expression.New(ci); _bodyList.Add(Expression.Assign(_vResult, resultInstance)); }
public static LoopExpression Loop(Expression body, LabelTarget @break, LabelTarget @continue) { RequiresCanRead(body, "body"); // TODO: lift the restriction on break, and allow loops to have non-void type ContractUtils.Requires(@break == null || @break.Type == typeof(void), "break", Strings.LabelTypeMustBeVoid); ContractUtils.Requires(@continue == null || @continue.Type == typeof(void), "continue", Strings.LabelTypeMustBeVoid); return new LoopExpression(body, @break, @continue); }
public override Expression Compile(ParameterExpression stateParameterExpression, LabelTarget returnTarget, LogicExpression valueExpression) { var value = this.Target.Compile(stateParameterExpression, returnTarget); var convertedValue = Expression.Convert(value, typeof(LogicStructureInstance)); var valueVariable = Expression.Variable(typeof(LogicStructureInstance), "value"); var field = Expression.Variable(typeof(LogicField), "field"); Expression<Func<LogicStructureInstance, string, LogicField>> lookupField = (x, z) => x.Fields.Keys.First(y => y.Name == z); var assignValue = Expression.Assign(valueVariable, convertedValue); var assignFieldName = Expression.Assign( field, Expression.Invoke(lookupField, valueVariable, Expression.Constant(this.Field))); var assignField = Expression.Assign( Expression.Property(Expression.Property(valueVariable, "Fields"), "Item", field), Expression.Convert(valueExpression.Compile(stateParameterExpression, returnTarget), typeof(object))); var assignFieldSet = Expression.Assign( Expression.Property(Expression.Property(valueVariable, "FieldsSet"), "Item", field), Expression.Constant(true)); return Expression.Block( new[] { valueVariable, field }, assignValue, assignFieldName, assignField, assignFieldSet); }
public LoopExpression Update (LabelTarget breakLabel, LabelTarget continueLabel, Expression body) { Contract.Requires(body != null); Contract.Requires(continueLabel == null || continueLabel.Type == typeof(void), "Continue label type must be void"); Contract.Ensures(Contract.Result<LoopExpression>() != null); return default(LoopExpression); }
public GotoExpression Update (LabelTarget target, Expression value) { Contract.Requires(target != null); Contract.Requires(value != null || target.Type == typeof(void), "Label type must be void when no value is provided"); Contract.Ensures(Contract.Result<GotoExpression>() != null); return default(GotoExpression); }
public ForExpression Update(ParameterExpression variable, Expression initializer, Expression test, Expression step, Expression body, LabelTarget breakTarget, LabelTarget continueTarget) { if (this.variable == variable && this.initializer == initializer && this.test == test && this.step == step && this.body == body && this.break_target == breakTarget && this.continue_target == continueTarget) return this; return CustomExpression.For(variable, initializer, test, step, body, breakTarget, continueTarget); }
public ForEachExpression Update(ParameterExpression variable, Expression enumerable, Expression body, LabelTarget breakTarget, LabelTarget continueTarget) { if (this.variable == variable && this.enumerable == enumerable && this.body == body && break_target == breakTarget && continue_target == continueTarget) return this; return CustomExpression.ForEach(variable, enumerable, body, continueTarget, breakTarget); }
public Expression Update(LabelTarget target, Type type, Expression value) { if (Target.Equals(target) && Type.Equals(type) && Value.Equals(value)) { return this; } return AstExpression.Init(_variableInitializer, ParentScope, Visitor); }
public Expression Update(LabelTarget target, Type type, Expression value) { if (Target.Equals(target) && Type.Equals(type) && Value.Equals(value)) { return this; } return AstExpression.Break(_breakStatement, ParentScope, Visitor); }
public AplusScope(AplusScope parent, string name, Aplus runtime = null, DLR.ParameterExpression runtimeParam = null, DLR.ParameterExpression moduleParam = null, DLR.LabelTarget returnTarget = null, bool isEval = false, bool isMethod = false, bool isAssignment = false) { this.parent = parent; this.name = name; this.runtime = runtime; this.runtimeParam = runtimeParam; this.moduleParam = moduleParam; this.returnTarget = returnTarget; this.variables = new Dictionary<string, DLR.ParameterExpression>(); this.callbackInfo = new CallbackInfoStorage(); this.iseval = isEval; this.ismethod = isMethod; this.isAssignment = isAssignment; InheritProperties(parent); }
internal GotoExpression(GotoExpressionKind kind, LabelTarget target, Expression value, Type type) { _kind = kind; _value = value; _target = target; _type = type; }
public override Expression Compile(ParameterExpression stateParameterExpression, LabelTarget returnTarget) { return Expression.Property( Expression.Property(stateParameterExpression, "Variables"), "Item", Expression.Constant(this.Identifier)); }
internal void AddLabelInfo(LabelTarget target, LabelInfo info) { if (this.Labels == null) { this.Labels = new HybridReferenceDictionary<LabelTarget, LabelInfo>(); } this.Labels[target] = info; }
internal bool ContainsTarget(LabelTarget target) { if (this.Labels == null) { return false; } return this.Labels.ContainsKey(target); }
/// <summary> /// Creates a new expression that is like this one, but using the /// supplied children. If all of the children are the same, it will /// return this expression. /// </summary> /// <param name="breakLabel">The <see cref="BreakLabel"/> property of the result.</param> /// <param name="continueLabel">The <see cref="ContinueLabel"/> property of the result.</param> /// <param name="body">The <see cref="Body"/> property of the result.</param> /// <returns>This expression if no children changed, or an expression with the updated children.</returns> public LoopExpression Update(LabelTarget breakLabel, LabelTarget continueLabel, Expression body) { if (breakLabel == BreakLabel && continueLabel == ContinueLabel && body == Body) { return this; } return Expression.Loop(body, breakLabel, continueLabel); }
private MSAst.LambdaExpression CreateOuterGeneratorFactory(Type lambdaType) { MSAst.LabelTarget returnLabelTarget = Ast.Label(lambdaType.GetMethod("Invoke").ReturnType); MSAst.Expression body = Ast.Return( returnLabelTarget, Ast.Call( typeof(RuntimeOps), "CreateDebugGenerator", new[] { _generatorLabelTarget.Type }, Ast.Call( typeof(RuntimeOps).GetMethod("CreateFrameForGenerator"), _debugContextExpression, _functionInfo ) ) ); MSAst.LabelExpression returnLabel = null; if (returnLabelTarget.Type == typeof(void)) { returnLabel = Ast.Label(returnLabelTarget, AstUtils.Void(body)); } else { returnLabel = Ast.Label(returnLabelTarget, AstUtils.Convert(body, returnLabelTarget.Type)); } return(Ast.Lambda( lambdaType, Ast.Block( _lambdaVars, returnLabel ), _alias, _lambdaParams)); }
internal override lambda.Expression CompileArrayBlock(lambda.ParameterExpression paramArray1, lambda.LabelTarget fault) { lambda.ParameterExpression counter = lambda.Expression.Variable(typeof(int), "counter"); lambda.ParameterExpression countitem = lambda.Expression.Variable(typeof(int), "countitem"); lambda.LabelTarget label = lambda.Expression.Label(typeof(object)); lambda.BlockExpression block = lambda.Expression.Block( new[] { counter, countitem }, lambda.Expression.Assign(counter, lambda.Expression.Constant(0)), lambda.Expression.Assign(countitem, lambda.Expression.Constant(0)), lambda.Expression.Loop( lambda.Expression.IfThenElse( lambda.Expression.LessThan(counter, lambda.Expression.ArrayLength(paramArray1)), lambda.Expression.Block( lambda.Expression.TryCatch(lambda.Expression.Block( lambda.Expression.IfThen(lambda.Expression.IsTrue(lambda.Expression.Convert(lambda.Expression.ArrayIndex(paramArray1, counter), typeof(bool))), lambda.Expression.PostIncrementAssign(countitem)), countitem), lambda.Expression.Catch(typeof(Exception), countitem)), lambda.Expression.PostIncrementAssign(counter)), lambda.Expression.Break(label, lambda.Expression.Convert(countitem, typeof(object))) ), label)); return(block); }
public override DLR.Expression Generate(AplusScope scope) { // This parameter will store the return value DLR.ParameterExpression returnValue = DLR.ParameterExpression.Parameter(typeof(AType), "RETURN_VALUE"); DLR.LabelTarget breakLabel = DLR.Expression.Label(typeof(AType), "BREAK"); DLR.Expression result = DLR.Expression.Block( new DLR.ParameterExpression[] { returnValue }, // Assign the default return value: ANull DLR.Expression.Assign(returnValue, DLR.Expression.Constant(Utils.ANull())), DLR.Expression.Loop( DLR.Expression.Block( DLR.Expression.IfThen( // Test if the condition is equal to 0 // Invert the inner test's result DLR.Expression.Not( // This part will test if the condition is true (this means it is not 0) DLR.Expression.IsTrue( this.expression.Generate(scope), typeof(Helpers).GetMethod("BooleanTest") ) ), // Break out from the loop with the last computed value DLR.Expression.Break(breakLabel, returnValue) ), // Compute & assign the value DLR.Expression.Assign(returnValue, this.codeBlock.Generate(scope)) ), // The label where to jump in case of break breakLabel ) ); return(result); }
public void EnterBlockDefinition( ScopeBuilder /*!*/ locals, MSA.Expression /*!*/ bfcVariable, MSA.Expression /*!*/ selfVariable, MSA.ParameterExpression /*!*/ runtimeScopeVariable, MSA.LabelTarget /*!*/ redoLabel) { Assert.NotNull(locals, bfcVariable, selfVariable); Assert.NotNull(redoLabel); BlockScope block = new BlockScope(locals, selfVariable, runtimeScopeVariable, bfcVariable, redoLabel); block.Parent = _currentElement; block.ParentRescue = _currentRescue; block.ParentLoop = _currentLoop; block.ParentBlock = _currentBlock; block.ParentVariableScope = _currentVariableScope; _currentElement = block; _currentRescue = null; _currentLoop = null; _currentBlock = block; _currentVariableScope = block; }
internal MSA.Expression /*!*/ Transform(AstGenerator /*!*/ gen, bool isLambda) { ScopeBuilder scope = DefineLocals(gen.CurrentScope); // define hidden parameters and RHS-placeholders (#1..#n will be used as RHS of a parallel assignment): MSA.ParameterExpression blockParameter, selfParameter; var parameters = DefineParameters(out selfParameter, out blockParameter); MSA.ParameterExpression scopeVariable = scope.DefineHiddenVariable("#scope", typeof(RubyBlockScope)); MSA.LabelTarget redoLabel = Ast.Label(); gen.EnterBlockDefinition( scope, blockParameter, selfParameter, scopeVariable, redoLabel ); MSA.Expression paramInit = MakeParametersInitialization(gen, parameters); MSA.ParameterExpression blockUnwinder, filterVariable; MSA.Expression traceCall, traceReturn; if (gen.TraceEnabled) { int firstStatementLine = _body.Count > 0 ? _body.First.Location.Start.Line : Location.End.Line; int lastStatementLine = _body.Count > 0 ? _body.Last.Location.End.Line : Location.End.Line; traceCall = Methods.TraceBlockCall.OpCall(scopeVariable, blockParameter, gen.SourcePathConstant, AstUtils.Constant(firstStatementLine)); traceReturn = Methods.TraceBlockReturn.OpCall(scopeVariable, blockParameter, gen.SourcePathConstant, AstUtils.Constant(lastStatementLine)); } else { traceCall = traceReturn = Ast.Empty(); } MSA.Expression body = AstUtils.Try( paramInit, traceCall, Ast.Label(redoLabel), AstUtils.Try( gen.TransformStatements(_body, ResultOperation.Return) ).Catch(blockUnwinder = Ast.Parameter(typeof(BlockUnwinder), "#u"), // redo: AstUtils.IfThen(Ast.Field(blockUnwinder, BlockUnwinder.IsRedoField), Ast.Goto(redoLabel)), // next: gen.Return(Ast.Field(blockUnwinder, BlockUnwinder.ReturnValueField)) ) ).Filter(filterVariable = Ast.Parameter(typeof(Exception), "#e"), Methods.FilterBlockException.OpCall(scopeVariable, filterVariable) ).Finally( traceReturn, Ast.Empty() ); body = gen.AddReturnTarget( scope.CreateScope( scopeVariable, Methods.CreateBlockScope.OpCall(new AstExpressions { scope.MakeLocalsStorage(), scope.GetVariableNamesExpression(), blockParameter, selfParameter, EnterInterpretedFrameExpression.Instance }), body ) ); gen.LeaveBlockDefinition(); int parameterCount = ParameterCount; var attributes = _parameters.GetBlockSignatureAttributes(); var dispatcher = Ast.Constant( BlockDispatcher.Create(parameterCount, attributes, gen.SourcePath, Location.Start.Line), typeof(BlockDispatcher) ); return(Ast.Coalesce( (isLambda ? Methods.InstantiateLambda : Methods.InstantiateBlock).OpCall(gen.CurrentScopeVariable, gen.CurrentSelfVariable, dispatcher), (isLambda ? Methods.DefineLambda : Methods.DefineBlock).OpCall(gen.CurrentScopeVariable, gen.CurrentSelfVariable, dispatcher, BlockDispatcher.CreateLambda( body, RubyStackTraceBuilder.EncodeMethodName(gen.CurrentMethod.MethodName, gen.SourcePath, Location, gen.DebugMode), parameters, parameterCount, attributes ) ) )); }
/// <summary> /// Gets the debug view for the specified label. /// </summary> /// <param name="label">The label to get a debug view for.</param> /// <returns>Debug view for the specified label.</returns> public XNode GetDebugView(LabelTarget label) { return(Visit(label)); }
/// <summary> /// Creates a <see cref="LabelExpression" /> representing a label with no default value. /// </summary> /// <param name="target">The <see cref="LabelTarget" /> which this <see cref="LabelExpression" /> will be associated with.</param> /// <returns>A <see cref="LabelExpression" /> with no default value.</returns> public static LabelExpression Label(LabelTarget target) { return(Label(target, null)); }
internal LabelExpression(LabelTarget label, Expression defaultValue) { Target = label; DefaultValue = defaultValue; }
private int GetLabelTargetId(LabelTarget target) { Debug.Assert(string.IsNullOrEmpty(target.Name)); return(GetId(target, ref _labelIds)); }
/// <summary> /// Creates a <see cref="LoopExpression"/> with the given body and break target. /// </summary> /// <param name="body">The body of the loop.</param> /// <param name="break">The break target used by the loop body.</param> /// <returns>The created <see cref="LoopExpression"/>.</returns> public static LoopExpression Loop(Expression body, LabelTarget @break) { return(Loop(body, @break, null)); }
public void EnterLoop(MSA.Expression /*!*/ redoVariable, MSA.Expression /*!*/ resultVariable, MSA.LabelTarget /*!*/ breakLabel, MSA.LabelTarget /*!*/ continueLabel) { Assert.NotNull(redoVariable, resultVariable, breakLabel, continueLabel); LoopScope loop = new LoopScope(redoVariable, resultVariable, breakLabel, continueLabel); loop.Parent = _currentElement; loop.ParentLoop = _currentLoop; _currentElement = _currentLoop = loop; }
public LoopExpression Update(LabelTarget breakLabel, LabelTarget continueLabel, Expression body) { throw new NotImplementedException(); }
internal static MSA.Expression /*!*/ MakeUserMethodBody(AstGenerator gen, int lastLine, MSA.Expression /*!*/ blockParameter, MSA.Expression /*!*/ rfcVariable, MSA.ParameterExpression /*!*/ methodUnwinder, MSA.Expression /*!*/ bodyStatement, ResultOperation resultOperation, int profileTickIndex, MSA.ParameterExpression stampVariable, MSA.LabelTarget returnLabel) { Assert.NotNull(blockParameter, rfcVariable, bodyStatement, methodUnwinder); Debug.Assert(!resultOperation.IsIgnore, "return value should not be ignored"); Debug.Assert(returnLabel != null || resultOperation.Variable != null, "return label needed"); MSA.Expression resultExpression = Ast.Field(methodUnwinder, MethodUnwinder.ReturnValueField); if (resultOperation.Variable != null) { resultExpression = Ast.Assign(resultOperation.Variable, resultExpression); } else { resultExpression = Ast.Return(returnLabel, resultExpression); } // TODO: move this to the caller: MSA.Expression profileStart, profileEnd; if (stampVariable != null) { profileStart = Ast.Assign(stampVariable, Methods.Stopwatch_GetTimestamp.OpCall()); profileEnd = Methods.UpdateProfileTicks.OpCall(Ast.Constant(profileTickIndex), stampVariable); } else { profileStart = profileEnd = Ast.Empty(); } return(AstUtils.Try( // initialize frame (RFC): profileStart, Ast.Assign(rfcVariable, Methods.CreateRfcForMethod.OpCall(AstUtils.Convert(blockParameter, typeof(Proc)))), bodyStatement ).Filter(methodUnwinder, Ast.Equal(Ast.Field(methodUnwinder, MethodUnwinder.TargetFrameField), rfcVariable), // return unwinder.ReturnValue; resultExpression ).Finally( Ast.Assign(Ast.Field(rfcVariable, RuntimeFlowControl.IsActiveMethodField), Ast.Constant(false)), profileEnd, gen != null && gen.TraceEnabled ? Methods.TraceMethodReturn.OpCall( gen.CurrentScopeVariable, Ast.Convert(Ast.Constant(gen.SourceUnit.Path), typeof(string)), Ast.Constant(lastLine) ) : Ast.Empty() )); }
// see Ruby Language.doc/Runtime/Control Flow Implementation/While-Until internal override MSA.Expression /*!*/ TransformRead(AstGenerator /*!*/ gen) { MSA.Expression resultVariable = gen.CurrentScope.DefineHiddenVariable("#loop-result", typeof(object)); MSA.Expression redoVariable = gen.CurrentScope.DefineHiddenVariable("#skip-condition", typeof(bool)); MSA.ParameterExpression unwinder; bool isInnerLoop = gen.CurrentLoop != null; MSA.LabelTarget breakLabel = Ast.Label(); MSA.LabelTarget continueLabel = Ast.Label(); gen.EnterLoop(redoVariable, resultVariable, breakLabel, continueLabel); MSA.Expression transformedBody = gen.TransformStatements(_statements, ResultOperation.Ignore); MSA.Expression transformedCondition = _condition.TransformCondition(gen, true); gen.LeaveLoop(); MSA.Expression conditionPositiveStmt, conditionNegativeStmt; if (_isWhileLoop) { conditionPositiveStmt = AstUtils.Empty(); conditionNegativeStmt = Ast.Break(breakLabel); } else { conditionPositiveStmt = Ast.Break(breakLabel); conditionNegativeStmt = AstUtils.Empty(); } // make the loop first: MSA.Expression loop = new AstBlock { gen.ClearDebugInfo(), Ast.Assign(redoVariable, AstUtils.Constant(_isPostTest)), AstFactory.Infinite(breakLabel, continueLabel, AstUtils.Try( AstUtils.If(redoVariable, Ast.Assign(redoVariable, AstUtils.Constant(false)) ).ElseIf(transformedCondition, conditionPositiveStmt ).Else( conditionNegativeStmt ), transformedBody, AstUtils.Empty() ).Catch(unwinder = Ast.Parameter(typeof(BlockUnwinder), "#u"), // redo = u.IsRedo Ast.Assign(redoVariable, Ast.Field(unwinder, BlockUnwinder.IsRedoField)), AstUtils.Empty() ).Filter(unwinder = Ast.Parameter(typeof(EvalUnwinder), "#u"), Ast.Equal(Ast.Field(unwinder, EvalUnwinder.ReasonField), AstFactory.BlockReturnReasonBreak), // result = unwinder.ReturnValue Ast.Assign(resultVariable, Ast.Field(unwinder, EvalUnwinder.ReturnValueField)), Ast.Break(breakLabel) ) ), gen.ClearDebugInfo(), AstUtils.Empty(), }; // wrap it to try finally that updates RFC state: if (!isInnerLoop) { loop = AstUtils.Try( Methods.EnterLoop.OpCall(gen.CurrentScopeVariable), loop ).Finally( Methods.LeaveLoop.OpCall(gen.CurrentScopeVariable) ); } return(Ast.Block(loop, resultVariable)); }
internal override MSA.Expression /*!*/ Transform(AstGenerator /*!*/ gen) { MSA.Expression parentScope = gen.CurrentScopeVariable; ScopeBuilder scope = new ScopeBuilder(); // define hidden parameters and RHS-placeholders (#1..#n will be used as RHS of a parallel assignment): MSA.Expression blockParameter, selfParameter; MSA.ParameterExpression[] parameters = DefineParameters(out selfParameter, out blockParameter); MSA.Expression scopeVariable = scope.DefineHiddenVariable("#scope", typeof(RubyBlockScope)); MSA.LabelTarget redoLabel = Ast.Label(); gen.EnterBlockDefinition( scope, blockParameter, selfParameter, scopeVariable, redoLabel ); if (_definedScope != null) { _definedScope.TransformLocals(scope); } MSA.Expression paramInit = MakeParametersInitialization(gen, parameters); MSA.ParameterExpression blockUnwinder = scope.DefineHiddenVariable("#unwinder", typeof(BlockUnwinder)); MSA.Expression loop = AstFactory.Infinite(null, redoLabel, AstUtils.Try( gen.TransformStatements(_body, ResultOperation.Return) ).Catch(blockUnwinder, // redo: AstUtils.IfThen(Ast.Field(blockUnwinder, BlockUnwinder.IsRedoField), Ast.Continue(redoLabel)), // next: gen.Return(Ast.Field(blockUnwinder, BlockUnwinder.ReturnValueField)) ) ); if (gen.TraceEnabled) { int firstStatementLine = _body.Count > 0 ? _body[0].Location.Start.Line : Location.End.Line; int lastStatementLine = _body.Count > 0 ? _body[_body.Count - 1].Location.End.Line : Location.End.Line; loop = Ast.TryFinally( Ast.Block( Methods.TraceBlockCall.OpCall(scopeVariable, blockParameter, Ast.Convert(Ast.Constant(gen.SourceUnit.Path), typeof(string)), Ast.Constant(firstStatementLine)), loop ), Methods.TraceBlockReturn.OpCall(scopeVariable, blockParameter, Ast.Convert(Ast.Constant(gen.SourceUnit.Path), typeof(string)), Ast.Constant(lastStatementLine)) ); } MSA.Expression body = Ast.Block( Ast.Assign(scopeVariable, Methods.CreateBlockScope.OpCall(scope.VisibleVariables(), parentScope, blockParameter, selfParameter) ), paramInit, loop, Ast.Empty() ); body = gen.AddReturnTarget(scope.CreateScope(body)); gen.LeaveBlockDefinition(); int parameterCount = _parameters.LeftValues.Count; var attributes = _parameters.GetBlockSignatureAttributes(); return(Methods.DefineBlock.OpCall( gen.CurrentScopeVariable, gen.CurrentRfcVariable, gen.CurrentSelfVariable, Ast.Lambda( BlockDispatcher.GetDelegateType(parameterCount, attributes), body, gen.EncodeMethodName(gen.CurrentMethod.MethodName, Location), new ReadOnlyCollection <MSA.ParameterExpression>(parameters) ), Ast.Constant(parameterCount), Ast.Constant(attributes) )); }
internal override lambda.Expression CompileArrayBlock(lambda.ParameterExpression paramArray1, lambda.LabelTarget fault) { lambda.ParameterExpression counter = lambda.Expression.Variable(typeof(int), "counter"); lambda.ParameterExpression exc = lambda.Expression.Variable(typeof(bool), "exc"); lambda.ParameterExpression row = lambda.Expression.Variable(typeof(object[]), "row"); lambda.ParameterExpression ret = lambda.Expression.Variable(typeof(object[]), "ret"); lambda.LabelTarget label = lambda.Expression.Label(typeof(object)); lambda.LabelTarget loclalfault = lambda.Expression.Label(); lambda.LabelTarget loclalsucces = lambda.Expression.Label(); lambda.BlockExpression foorEachBlock = lambda.Expression.Block( new[] { counter, ret, exc }, lambda.Expression.Assign(exc, lambda.Expression.Constant(false)), lambda.Expression.Assign(counter, lambda.Expression.Constant(0)), lambda.Expression.Assign(ret, lambda.Expression.Convert(lambda.Expression.ArrayIndex(paramArray1, lambda.Expression.Subtract(lambda.Expression.ArrayLength(paramArray1), lambda.Expression.Constant(1))), typeof(object[]))), // lambda.Expression.NewArrayBounds(typeof(object), lambda.Expression.ArrayLength(paramArray1))), lambda.Expression.Loop(lambda.Expression.IfThenElse( lambda.Expression.LessThan(counter, lambda.Expression.Subtract(lambda.Expression.ArrayLength(paramArray1), lambda.Expression.Constant(1))), lambda.Expression.Block( new[] { row }, lambda.Expression.TryCatch( lambda.Expression.Block( lambda.Expression.Assign(row, lambda.Expression.Convert(lambda.Expression.ArrayIndex(paramArray1, counter), typeof(object[]))), lambda.Expression.Assign(lambda.Expression.ArrayAccess(ret, counter), lambda.Expression.Convert(base.Compile(row, loclalfault), typeof(object))), lambda.Expression.Goto(loclalsucces), lambda.Expression.Label(loclalfault), lambda.Expression.Assign(lambda.Expression.ArrayAccess(ret, counter), lambda.Expression.Constant(null)), lambda.Expression.Label(loclalsucces), ret) , lambda.Expression.Catch(typeof(Exception), lambda.Expression.Block( lambda.Expression.Assign(counter, lambda.Expression.Subtract(lambda.Expression.ArrayLength(paramArray1), lambda.Expression.Constant(1))), lambda.Expression.Assign(exc, lambda.Expression.Constant(true)), ret))) , lambda.Expression.PostIncrementAssign(counter) ), lambda.Expression.IfThenElse(exc, lambda.Expression.Goto(fault), lambda.Expression.Break(label, lambda.Expression.Convert(ret, typeof(object)))) ), label) ); return(foorEachBlock); }
public override DLR.Expression Generate(AplusScope scope) { // TODO: Add usage of Protected Execute Flag // Save the previous return target DLR.LabelTarget oldTarget = scope.ReturnTarget; scope.ReturnTarget = DLR.Expression.Label(typeof(AType), "EXIT"); DLR.Expression protectedCode = DLR.Expression.Label( scope.ReturnTarget, this.codeblock.Generate(scope) ); // Restore the return target; scope.ReturnTarget = oldTarget; // Code block contining the strandard execution's result // wrapped in a strand DLR.Expression block = DLR.Expression.Call( typeof(Runtime.Helpers).GetMethod("BuildStrand"), DLR.Expression.NewArrayInit( typeof(AType), // We need to pass in reverse order protectedCode, DLR.Expression.Constant(AInteger.Create(0), typeof(AType)) ) ); // Parameter for Catch block DLR.ParameterExpression errorVariable = DLR.Expression.Parameter(typeof(Error), "error"); // Catch block, returns the ([errorcode]; [errortext]) strand DLR.CatchBlock catchBlock = DLR.Expression.Catch( errorVariable, DLR.Expression.Call( typeof(Runtime.Helpers).GetMethod("BuildStrand"), DLR.Expression.NewArrayInit( typeof(AType), // We need to pass in reverse order // Error Text DLR.Expression.Call( typeof(Runtime.Helpers).GetMethod("BuildString"), DLR.Expression.Property(errorVariable, "ErrorText") ), // Error Code DLR.Expression.Call( typeof(AInteger).GetMethod("Create", new Type[] { typeof(int) }), DLR.Expression.Convert( DLR.Expression.Property(errorVariable, "ErrorType"), typeof(int) ) ) ) ) ); DLR.Expression result = DLR.Expression.TryCatch( block, catchBlock ); return(result); }
public LoopScope(MSA.Expression /*!*/ redoVariable, MSA.Expression /*!*/ resultVariable, MSA.LabelTarget /*!*/ breakLabel, MSA.LabelTarget /*!*/ continueLabel) { Assert.NotNull(redoVariable, resultVariable, breakLabel, continueLabel); _redoVariable = redoVariable; _resultVariable = resultVariable; _breakLabel = breakLabel; _continueLabel = continueLabel; }
public RescueScope(MSA.Expression /*!*/ retryingVariable, MSA.LabelTarget /*!*/ retryLabel) { Assert.NotNull(retryingVariable, retryLabel); _retryingVariable = retryingVariable; _retryLabel = retryLabel; }
private static Ex enumeratorConversion(Type to, Ex enumerator, Type eType, LambdaExpression[] converters, Ex[] res, System.Linq.Expressions.LabelTarget end) { return(Ex.Block(res.Zip(converters, (r, con) => Ex.Block( Ex.IfThenElse( enumerator.Type.GetTypeInfo().GetDeclaredMethod(nameof(IEnumerator.MoveNext)) == null ? Ex.Call(Ex.Convert(enumerator, typeof(IEnumerator)), nameof(IEnumerator.MoveNext), Type.EmptyTypes) : Ex.Call(enumerator, enumerator.Type.GetTypeInfo().GetDeclaredMethod(nameof(IEnumerator.MoveNext))), Ex.Assign(r, con.ApplyTo(Ex.Property(enumerator, nameof(IEnumerator.Current)))), Ex.Goto(end, NoResult(to))), Ex.IfThen(Ex.Not(Ex.Property(r, nameof(IConversionResult.IsSuccessful))), Ex.Goto(end, NoResult(to))))))); }
public override DLR.Expression Generate(AplusScope scope) { Aplus runtime = scope.GetRuntime(); LinkedList <DLR.Expression> result = new LinkedList <DLR.Expression>(); DLR.ParameterExpression scalar = DLR.Expression.Parameter(typeof(AType), "_ScalarResult_"); DLR.ParameterExpression counter = DLR.Expression.Parameter(typeof(int), "COUNTER"); DLR.ParameterExpression exitValue = DLR.Expression.Parameter(typeof(int), "EXITVALUE"); DLR.LabelTarget exitLabel = DLR.Expression.Label(typeof(AType), "EXIT"); DLR.ParameterExpression returnValue = DLR.Expression.Parameter(typeof(AType), "RETURN"); bool incrementMode = true; if (this.expression is MonadicFunction && ((MonadicFunction)this.expression).Token.Type == Tokens.EXPONENTIAL) { // Change the counter's 'way' incrementMode = false; // Remove the Exponential function this.expression = ((MonadicFunction)this.expression).Expression; } if (this.expression is Assign && ((Assign)this.expression).Target is Identifier) { scope.IsAssignment = true; result.AddFirst(this.expression.Generate(scope)); scope.IsAssignment = false; // Remove the assignment and leave the identifier only this.expression = ((Assign)this.expression).Target; } // Save the previous return target DLR.LabelTarget oldTarget = scope.ReturnTarget; // Add an return target for the scope // this will allow the usage of the Result monadic function scope.ReturnTarget = exitLabel; if (this.expression is Identifier) { // Found a case like: VAR do { ... } Identifier variable = (Identifier)this.expression; // Generate a .Dynamic.Get DLR tree (used multiple times so this saves time) DLR.Expression variableGenerated = variable.Generate(scope); DLR.Expression variableAsFloat = DLR.Expression.Property(scalar, "asFloat"); result.AddLast(DLR.Expression.Block( new DLR.ParameterExpression[] { counter, exitValue, returnValue, scalar }, // Test if the constant is an integer DomainTest(variableGenerated, scalar), DLR.Expression.Assign(exitValue, (incrementMode ? // EXITVALUE = round(variable.asFloat) (DLR.Expression)FloatRounding(variableAsFloat) : // EXITVALUE = 0 (DLR.Expression)DLR.Expression.Constant(0, typeof(int)) ) ), DLR.Expression.Assign( counter, (incrementMode ? (DLR.Expression)DLR.Expression.Constant(0, typeof(int)) : (DLR.Expression)DLR.Expression.Decrement(FloatRounding(variableAsFloat)) ) ), // Start the loop DLR.Expression.Loop( DLR.Expression.Block( AST.Assign.GenerateIdentifierAssign( scope, variable, DLR.Expression.Call(typeof(LocalAInteger).GetMethod("Create"), counter), false, false ), DLR.Expression.IfThen( (incrementMode ? // Check if variable >= EXITVALUE is true DLR.Expression.GreaterThanOrEqual( counter, //DLR.Expression.Property(variableGenerated, "asInteger"), exitValue ) : // Check if EXITVALUE(0) > variable is true DLR.Expression.GreaterThan( exitValue, //DLR.Expression.Property(variableGenerated, "asInteger") counter ) ), // The expression was true, exit from the loop with the last value of the expression block DLR.Expression.Break(exitLabel, returnValue) ), // Otherwise run the inner codeblock DLR.Expression.Assign(returnValue, this.codeblock.Generate(scope)), // Update counter (incrementMode ? // ++counter DLR.Expression.PreIncrementAssign(counter) : // --counter DLR.Expression.PreDecrementAssign(counter) ) ), exitLabel ) )); } else { // Simple Iteration DLR.ParameterExpression temp = DLR.Expression.Parameter(typeof(AType), "TMP"); result.AddLast(DLR.Expression.Block( new DLR.ParameterExpression[] { temp, counter, exitValue, returnValue, scalar }, // Save the iteration count into a temporaly variable DLR.Expression.Assign(temp, this.expression.Generate(scope)), // Test if the constant is an integer DomainTest(temp, scalar), // MAXVALUE = temp.asInteger DLR.Expression.Assign(exitValue, FloatRounding(DLR.Expression.Property(scalar, "asFloat"))), // counter = 0 DLR.Expression.Assign(counter, DLR.Expression.Constant(0, typeof(int))), // Start the loop DLR.Expression.Loop( DLR.Expression.Block( // Check if counter >= MAXVALUE is true DLR.Expression.IfThen( DLR.Expression.GreaterThanOrEqual(counter, exitValue), // The expression was true, exit from the loop with the last calculated value DLR.Expression.Break(exitLabel, returnValue) ), // Otherwise run the inner codeblock, save the block's result DLR.Expression.Assign(returnValue, this.codeblock.Generate(scope)), // Increment the counter DLR.Expression.PreIncrementAssign(counter) ), exitLabel ) )); } // Restore the return target scope.ReturnTarget = oldTarget; return(DLR.Expression.Block(result)); }
public LoopExpression Update(LabelTarget breakLabel, LabelTarget continueLabel, Expression body) { return(default(LoopExpression)); }
private void DumpLabel(LabelTarget target) { Out(string.Format(CultureInfo.CurrentCulture, ".LabelTarget {0}:", GetLabelTargetName(target))); }
internal static MSAst.Expression TransformFor(ScopeStatement parent, MSAst.ParameterExpression enumerator, Expression list, Expression left, MSAst.Expression body, Statement else_, SourceSpan span, SourceLocation header, MSAst.LabelTarget breakLabel, MSAst.LabelTarget continueLabel, bool isStatement) { // enumerator, isDisposable = Dynamic(GetEnumeratorBinder, list) MSAst.Expression init = Ast.Assign( enumerator, new PythonDynamicExpression1 <KeyValuePair <IEnumerator, IDisposable> >( Binders.UnaryOperationBinder( parent.GlobalParent.PyContext, PythonOperationKind.GetEnumeratorForIteration ), parent.GlobalParent.CompilationMode, AstUtils.Convert(list, typeof(object)) ) ); // while enumerator.MoveNext(): // left = enumerator.Current // body // else: // else MSAst.Expression ls = AstUtils.Loop( parent.GlobalParent.AddDebugInfo( Ast.Call( Ast.Property( enumerator, typeof(KeyValuePair <IEnumerator, IDisposable>).GetProperty("Key") ), typeof(IEnumerator).GetMethod("MoveNext") ), left.Span ), null, Ast.Block( left.TransformSet( SourceSpan.None, Ast.Call( Ast.Property( enumerator, typeof(KeyValuePair <IEnumerator, IDisposable>).GetProperty("Key") ), typeof(IEnumerator).GetProperty("Current").GetGetMethod() ), PythonOperationKind.None ), body, isStatement ? UpdateLineNumber(parent.GlobalParent.IndexToLocation(list.StartIndex).Line) : AstUtils.Empty(), AstUtils.Empty() ), else_, breakLabel, continueLabel ); return(Ast.Block( init, Ast.TryFinally( ls, Ast.Block( Ast.Call(AstMethods.ForLoopDispose, enumerator), Ast.Assign(enumerator, Ast.New(typeof(KeyValuePair <IEnumerator, IDisposable>))) ) ) )); }
private MSAst.LambdaExpression CreateOuterLambda(Type lambdaType, MSAst.Expression debuggableBody) { List <MSAst.Expression> bodyExpressions = new List <MSAst.Expression>(); List <MSAst.Expression> tryExpressions = new List <MSAst.Expression>(); List <MSAst.Expression> finallyExpressions = new List <MSAst.Expression>(); Type returnType = lambdaType.GetMethod("Invoke").ReturnType; MSAst.LabelTarget returnLabelTarget = Ast.Label(returnType); // Init $funcInfo tryExpressions.Add( Ast.Assign( _funcInfo, Ast.Convert(_functionInfo, typeof(FunctionInfo)) ) ); // Init $traceLocations // $TODO: only do this if we're in TracePoints mode tryExpressions.Add( Ast.Assign( _traceLocations, Ast.Call(typeof(RuntimeOps).GetMethod("GetTraceLocations"), _funcInfo) ) ); // Init sourceFile locals foreach (var entry in _sourceFilesMap) { tryExpressions.Add( Ast.Assign( entry.Value, Ast.Constant(entry.Key, typeof(DebugSourceFile)) ) ); } if (_noPushFrameOptimization) { tryExpressions.Add(_pushFrame); } tryExpressions.Add(Ast.Call( typeof(RuntimeOps).GetMethod("OnFrameEnterTraceEvent"), _thread )); var frameExit = AstUtils.If( Ast.Equal( _debugMarkerLocationMap.Length > 0 ? Ast.Property(_sourceFilesMap[_debugMarkerLocationMap[0].SourceFile], "Mode") : _globalDebugMode, AstUtils.Constant((int)DebugMode.FullyEnabled) ), Ast.Call( typeof(RuntimeOps).GetMethod("OnFrameExitTraceEvent"), _thread, _debugMarker, _retVal != null ? (MSAst.Expression)Ast.Convert(_retVal, typeof(object)) : Ast.Constant(null) ) ); // normal exit tryExpressions.Add( Ast.Block( _retVal != null ? Ast.Assign(_retVal, debuggableBody) : debuggableBody, Ast.Assign(_frameExitException, Ast.Constant(true)), frameExit) ); tryExpressions.Add( _retVal != null ? (MSAst.Expression)Ast.Return(returnLabelTarget, _retVal) : Ast.Empty() ); MSAst.Expression[] popFrame = new MSAst.Expression[] { AstUtils.If( // Fire thead-exit event if PopFrame returns true Ast.AndAlso( Ast.Equal(Ast.Call(typeof(RuntimeOps).GetMethod("PopFrame"), _thread), Ast.Constant(true)), Ast.Equal(_globalDebugMode, AstUtils.Constant((int)DebugMode.FullyEnabled)) ), Ast.Call( typeof(RuntimeOps).GetMethod("OnThreadExitEvent"), _thread ) ) }; if (_noPushFrameOptimization) { finallyExpressions.AddRange(popFrame); } else { finallyExpressions.Add( AstUtils.If( Ast.Equal(_framePushed, Ast.Constant(true)), popFrame ) ); } MSAst.ParameterExpression caughtException; // Run the function body bodyExpressions.Add(Ast.TryCatchFinally( Ast.TryCatch( Ast.Block( ArrayUtils.Append(tryExpressions.ToArray(), Ast.Default(returnType)) ), Ast.Catch( caughtException = Ast.Variable(typeof(Exception), "$caughtException"), Ast.Block( // The expressions below will always throw. // If the exception needs to be cancelled then OnTraceEvent will throw ForceToGeneratorLoopException. // If the exception is not being cancelled then we'll just rethrow at the end of the catch block. AstUtils.If( Ast.Not( Ast.TypeIs( caughtException, typeof(ForceToGeneratorLoopException) ) ), AstUtils.If( Ast.NotEqual(_globalDebugMode, AstUtils.Constant((int)DebugMode.Disabled)), _noPushFrameOptimization ? Ast.Empty() : _conditionalPushFrame, Ast.Call( typeof(RuntimeOps).GetMethod("OnTraceEventUnwind"), _thread, _debugMarker, caughtException ) ), // exception exit AstUtils.If( Ast.Not(_frameExitException), frameExit ) ), Ast.Rethrow(), // Ensuring that the catch block is of the same type as the try block Ast.Default(returnType) ) ) ), Ast.Block(finallyExpressions), Ast.Catch( typeof(ForceToGeneratorLoopException), Ast.TryFinally( // Handle ForceToGeneratorLoopException Ast.Block( returnType != typeof(void) ? Ast.Block( Ast.Assign( _retValFromGeneratorLoop, Ast.Call( typeof(RuntimeOps).GetMethod("GeneratorLoopProc"), _thread ) ), AstUtils.If( Ast.NotEqual( _retValFromGeneratorLoop, Ast.Constant(null) ), Ast.Assign(_retVal, Ast.Convert(_retValFromGeneratorLoop, returnType)), Ast.Return( returnLabelTarget, Ast.Convert(_retValFromGeneratorLoop, returnType) ) ).Else( Ast.Assign(_retVal, Ast.Default(returnType)), Ast.Return( returnLabelTarget, Ast.Default(returnType) ) ) ) : Ast.Block( Ast.Call( typeof(RuntimeOps).GetMethod("GeneratorLoopProc"), _thread ), Ast.Return(returnLabelTarget) ) , // Ensuring that the catch block is of the same type as the try block Ast.Default(returnType) ), // Make sure that the debugMarker is up-to-date after the generator loop Ast.Assign( _debugMarker, Ast.Call( typeof(RuntimeOps).GetMethod("GetCurrentSequencePointForLeafGeneratorFrame"), _thread ) ) ) ) )); MSAst.Expression body = Ast.Block(bodyExpressions); if (body.Type == typeof(void) && returnType != typeof(void)) { body = Ast.Block(body, Ast.Default(returnType)); } return(Ast.Lambda( lambdaType, Ast.Block( _lambdaVars, Ast.Label(returnLabelTarget, body) ), _alias, _lambdaParams)); }
private static DLR.Expression BuildDyadicCase( Token functionToken, DLR.LabelTarget returnTarget, DLR.Expression environment, DLR.Expression rightParam, DLR.Expression leftParam) { DLR.Expression result; MethodInfo method = typeof(AbstractDyadicFunction).GetMethod("Execute"); if (functionToken.Type == Tokens.TYPE) { result = DLR.Expression.IfThenElse( // $left.IsNumber || ($left.Type == ATypes.ANull) DLR.Expression.OrElse( DLR.Expression.IsTrue( DLR.Expression.PropertyOrField(leftParam, "IsNumber") ), DLR.Expression.Equal( DLR.Expression.PropertyOrField(leftParam, "Type"), DLR.Expression.Constant(ATypes.ANull) ) ), // Or($right, $left) DLR.Expression.Goto( returnTarget, DLR.Expression.Call( DLR.Expression.Constant(DyadicFunctionInstance.Or), method, rightParam, leftParam, environment ) ), // Cast($right, $left) DLR.Expression.Goto( returnTarget, DLR.Expression.Call( DLR.Expression.Constant(DyadicFunctionInstance.Cast), method, rightParam, leftParam, environment ) ) ); } else { MethodChooser.ConvertToDyadicToken(functionToken); AbstractDyadicFunction dyadic = MethodChooser.GetDyadicMethod(functionToken); if (dyadic != null) { result = DLR.Expression.Goto( returnTarget, DLR.Expression.Call( DLR.Expression.Constant(dyadic), method, rightParam, leftParam, environment ) ); } else { result = DLR.Expression.Throw( DLR.Expression.New( typeof(Error.Valence).GetConstructor(new Type[] { typeof(string) }), DLR.Expression.Constant(functionToken.Text) ) ); } } return(result); }
/// <summary> /// Creates a <see cref="LabelExpression" /> representing a label with the given default value. /// </summary> /// <param name="target">The <see cref="LabelTarget" /> which this <see cref="LabelExpression" /> will be associated with.</param> /// <param name="defaultValue"> /// The value of this <see cref="LabelExpression" /> when the label is reached through normal /// control flow. /// </param> /// <returns>A <see cref="LabelExpression" /> with the given default value.</returns> public static LabelExpression Label(LabelTarget target, Expression defaultValue) { ValidateGoto(target, ref defaultValue, nameof(target), nameof(defaultValue), null); return(new LabelExpression(target, defaultValue)); }
internal LoopExpression(Expression body, LabelTarget @break, LabelTarget @continue) { _body = body; _break = @break; _continue = @continue; }
public static MSA.Expression /*!*/ Infinite(MSA.LabelTarget @break, MSA.LabelTarget @continue, params MSA.Expression[] /*!*/ body) { return(AstUtils.Infinite(Ast.Block(body), @break, @continue)); }
internal virtual lambda.Expression Compile(lambda.Expression[] param, lambda.LabelTarget fault) { throw new EvaluateException("Syntax Error"); }