protected override Expression VisitTry(TryExpression node) { if (CallOriginal(node, out Object? result)) { return((Expression)result); } return(base.VisitTry(node)); }
public void UpdateTrySameChildrenDifferentCollectionsSameNode() { TryExpression tryExp = Expression.TryCatchFinally(Expression.Empty(), Expression.Empty(), Expression.Catch(typeof(Exception), Expression.Empty())); Assert.Same(tryExp, tryExp.Update(tryExp.Body, tryExp.Handlers.ToArray(), tryExp.Finally, null)); tryExp = Expression.TryFault(Expression.Empty(), Expression.Empty()); Assert.Same(tryExp, tryExp.Update(tryExp.Body, null, null, tryExp.Fault)); }
public void CannotReduceTry() { TryExpression tryExp = Expression.TryFault(Expression.Empty(), Expression.Empty()); Assert.False(tryExp.CanReduce); Assert.Same(tryExp, tryExp.Reduce()); Assert.Throws <ArgumentException>(() => tryExp.ReduceAndCheck()); }
public void UpdateTryDiffBodyDiffNode() { TryExpression tryExp = Expression.TryCatchFinally(Expression.Empty(), Expression.Empty(), Expression.Catch(typeof(Exception), Expression.Empty())); Assert.NotSame(tryExp, tryExp.Update(Expression.Empty(), tryExp.Handlers, tryExp.Finally, null)); tryExp = Expression.TryFault(Expression.Empty(), Expression.Empty()); Assert.NotSame(tryExp, tryExp.Update(Expression.Empty(), null, null, tryExp.Fault)); }
public void UpdateTrySameChildrenSameNode() { TryExpression tryExp = Expression.TryCatchFinally(Expression.Empty(), Expression.Empty(), Expression.Catch(typeof(Exception), Expression.Empty())); Assert.Same(tryExp, tryExp.Update(tryExp.Body, tryExp.Handlers, tryExp.Finally, tryExp.Fault)); tryExp = Expression.TryFault(Expression.Empty(), Expression.Empty()); Assert.Same(tryExp, tryExp.Update(tryExp.Body, tryExp.Handlers, tryExp.Finally, tryExp.Fault)); }
public static Func <NpgsqlDataReader, T> GetReader <T>() { Delegate resDelegate; if (!ExpressionCache.TryGetValue(typeof(T), out resDelegate)) { // Get the indexer property of NpgsqlDataReader var indexerProperty = typeof(NpgsqlDataReader).GetProperty("Item", typeof(object), new[] { typeof(string) }); // List of statements in our dynamic method var statements = new List <Expression>(); // Instance type of target entity class ParameterExpression instanceParam = Expression.Variable(typeof(T)); // Parameter for the NpgsqlDataReader object ParameterExpression readerParam = Expression.Parameter(typeof(NpgsqlDataReader)); // Create and assign new T to variable. Ex. var instance = new T(); BinaryExpression createInstance = Expression.Assign(instanceParam, Expression.New(typeof(T))); statements.Add(createInstance); foreach (var property in typeof(T).GetProperties()) { // instance.Property MemberExpression getProperty = Expression.Property(instanceParam, property); // row[property] The assumption is, column names are the // same as PropertyInfo names of T IndexExpression readValue = Expression.MakeIndex(readerParam, indexerProperty, new[] { Expression.Constant(property.Name) }); // instance.Property = row[property] UnaryExpression convertExpression = Expression.Convert(readValue, property.PropertyType); BinaryExpression assignProperty = Expression.Assign(getProperty, convertExpression); //needs a try block in case we don't fetch up all the fields on the model TryExpression tryExpression = Expression.TryCatch( assignProperty, Expression.Catch( typeof(Exception), Expression.Assign(getProperty, property.PropertyType == typeof(string) ? Expression.Convert(Expression.Constant(""), property.PropertyType) : Expression.Convert(Expression.Constant(0), property.PropertyType)))); statements.Add(tryExpression); //statements.Add(assignProperty); } var returnStatement = instanceParam; statements.Add(returnStatement); var body = Expression.Block(instanceParam.Type, new[] { instanceParam }, statements.ToArray()); var lambda = Expression.Lambda <Func <NpgsqlDataReader, T> >(body, readerParam); resDelegate = lambda.Compile(); // Cache the dynamic method into ExpressionCache dictionary ExpressionCache[typeof(T)] = resDelegate; } return((Func <NpgsqlDataReader, T>)resDelegate); }
private Expression RewriteTryCatch(TryExpression node) { // we inline the catch handlers after the catch blocks and use labels // to branch around and propagate the result out. // // goto tryDone( // try { // if (LightExceptions.IsLightException(_lastValue = someCall)) { // goto ehLabel; // } else { // _lastValue // } // } catch(Exception e) { // handler; // } // ) // // ehLabel: // if ((e = GetLightException(_lastValue) as Exception)) != null) { // handler; // } else { // // unhandled exception, propagate up, either: // goto _returnValue(_lastValue); // // if we weren't in a nested exception handler or if we were: // goto _ehLabelOuter; // } // tryDone: // // yields either the value of the try block or the real catch block // // from the goto tryDone or it gets it's default value from ehLabel // // which is branched to when an exception is detected. // var ehLabel = Expression.Label(typeof(void), GetEhLabelName("lightEh")); var tryDoneLabel = Expression.Label(node.Body.Type, GetEhLabelName("tryDone")); Expression body = Expression.Block( Expression.Goto( tryDoneLabel, Expression.TryCatch(RewriteTryBody(node, ehLabel), VisitHandlers(node, true)) ), Expression.Label( tryDoneLabel, Expression.Block( Expression.Label(ehLabel), Utils.Convert( LightCatch(VisitHandlers(node, false)), node.Body.Type ) ) ) ); // if we have a finally wrap the whole thing up now. if (node.Finally != null) { body = RewriteTryFinally(body, node.Finally); } return body; }
/// <summary> /// Visits the children of the <see cref="TryExpression"/>. /// </summary> /// <param name="node">The expression to visit.</param> /// <returns>The modified expression, if it or any subexpression was modified; /// otherwise, returns the original expression.</returns> protected override Expression VisitTry(TryExpression node) { return(node.Update( Visit(node.Body), Visit(node.Handlers, VisitCatchBlock), Visit(node.Finally), Visit(node.Fault) )); }
protected virtual int GetHashCode(TryExpression node, object state) { if (node == null) { return(0); } return(CombineHash(GetHashCode(node.Body, state), GetHashCode(node.Fault, state), GetHashCode(node.Finally, state), GetHashCode(node.Handlers, state, GetHashCode))); }
private Expression TransformX(TryExpression e) { var b = Transform(e.Body); var c = Transform(e.Handlers, TransformCatchBlock); var f = Transform(e.Finally); var t = Transform(e.Fault); return(e.Update(b, c, f, t)); }
protected override Expression VisitTry(TryExpression node) { if (!Options.HasFlag(ExpressionOptions.AllowTryBlocks)) { throw new ExpressionSecurityException("Try blocks are not permitted."); } return(base.VisitTry(node)); }
/// <summary> /// Visits the children of the <see cref="TryExpression" />. /// </summary> /// <param name="node">The expression to visit.</param> /// <returns>The modified expression, if it or any subexpression was modified; /// otherwise, returns the original expression.</returns> protected internal virtual Expression VisitTry(TryExpression node) { return(node.Update( Visit(node.Body), Visit(node.Handlers, VisitCatchBlock), Visit(node.Finally), Visit(node.Fault) )); }
protected virtual Expression VisitTry(TryExpression exp) { var body = this.Visit(exp.Body); var cb = this.VisitCatchBlocks(exp.Handlers); var fault = this.Visit(exp.Fault); var fin = this.Visit(exp.Finally); return(this.UpdateTry(exp, body, cb, fault, fin)); }
public void CanCatchAndThrowNonExceptionsInterpreted() { TryExpression throwCatchString = Expression.TryCatch( Expression.Throw(Expression.Constant("Hello")), Expression.Catch(typeof(string), Expression.Empty()) ); Expression.Lambda <Action>(throwCatchString).Compile(true)(); }
/// <summary> /// Return an expression from the method /// </summary> /// <param name="argumentContext"></param> /// <returns></returns> public (ParameterExpression, Expression) GetembeddedCallAction(Expression instance, Expression parameters, Expression[] arguments) { MethodCallExpression m = GetCallMethod(instance, arguments); MethodCallExpression m2 = EmbedLog(arguments, m, parameters); var variableResult = Expression.Variable(typeof(object), "result"); TryExpression _try = EmbedTryCatch(arguments, variableResult, m2, parameters); return(variableResult, _try); }
protected override Expression VisitTry(TryExpression node) { if (FromSubclass) { FromSubclass = false; return(base.VisitTry(node)); } throw new NotSupportedException(); }
private void InterpretCatchBlock(TryExpression expression, Exception e) { LeaveChildScope(true); EnterChildScope(); _currentScope.Add( expression.CatchArg.Identifier, new AphidObject(e.Message)); Interpret(expression.CatchBody, false); LeaveChildScope(true); }
public void Serialize(JsonObject json, Expression expression) { TryExpression @try = (TryExpression)expression; json["trytype"] = serializer.Write(@try.Type); json["body"] = serializer.Write(@try.Body); json["finally"] = serializer.Write(@try.Finally); json["fault"] = serializer.Write(@try.Fault); json["handlers"] = new JsonArray(@try.Handlers.Select(serializer.Write)); }
public void CanAccessExceptionCaughtInterpreted() { ParameterExpression variable = Expression.Variable(typeof(Exception)); TryExpression throwCatch = Expression.TryCatch( Expression.Throw(Expression.Constant(new TestException()), typeof(string)), Expression.Catch(variable, Expression.Property(variable, "Message")) ); Assert.Equal("This is a test exception", Expression.Lambda <Func <string> >(throwCatch).Compile(true)()); }
public TryStatementWithLinqExpressions(TryExpression statement) { Statement = statement; tryStatements = LinqStatementBuilder.BuildStatements(statement.Body); catchStatements = statement.Handlers.ToArray(@catch => new CatchStatementWithLinqExpressions(@catch)); if (statement.Finally != null) { finallyStatement = new FinallyStatementWithLinqExpressions(statement); } }
public void FinallyDoesNotDetermineValueSomethingCaughtInterpreted() { TryExpression finally2 = Expression.TryCatchFinally( Expression.Throw(Expression.Constant(new ArgumentException()), typeof(int)), Expression.Constant(2), Expression.Catch(typeof(ArgumentException), Expression.Constant(3)) ); Assert.Equal(3, Expression.Lambda <Func <int> >(finally2).Compile(true)()); }
public void FinallyDoesNotDetermineValueNothingCaughtInterpreted() { TryExpression finally2 = Expression.TryCatchFinally( Expression.Constant(1), Expression.Constant(2), Expression.Catch(typeof(object), Expression.Constant(3)) ); Assert.Equal(1, Expression.Lambda <Func <int> >(finally2).Compile(true)()); }
public bool Compare(Expression left, Expression right) { if (left == right) { return(true); } if (left == null || right == null) { return(false); } if (left.NodeType != right.NodeType) { return(false); } if (left.Type != right.Type) { return(false); } return(left switch { BinaryExpression leftBinary => CompareBinary(leftBinary, (BinaryExpression)right), BlockExpression leftBlock => CompareBlock(leftBlock, (BlockExpression)right), ConditionalExpression leftConditional => CompareConditional(leftConditional, (ConditionalExpression)right), ConstantExpression leftConstant => CompareConstant(leftConstant, (ConstantExpression)right), DefaultExpression _ => true, // Intentionally empty. No additional members GotoExpression leftGoto => CompareGoto(leftGoto, (GotoExpression)right), IndexExpression leftIndex => CompareIndex(leftIndex, (IndexExpression)right), InvocationExpression leftInvocation => CompareInvocation(leftInvocation, (InvocationExpression)right), LabelExpression leftLabel => CompareLabel(leftLabel, (LabelExpression)right), LambdaExpression leftLambda => CompareLambda(leftLambda, (LambdaExpression)right), ListInitExpression leftListInit => CompareListInit(leftListInit, (ListInitExpression)right), LoopExpression leftLoop => CompareLoop(leftLoop, (LoopExpression)right), MemberExpression leftMember => CompareMember(leftMember, (MemberExpression)right), MemberInitExpression leftMemberInit => CompareMemberInit(leftMemberInit, (MemberInitExpression)right), MethodCallExpression leftMethodCall => CompareMethodCall(leftMethodCall, (MethodCallExpression)right), NewArrayExpression leftNewArray => CompareNewArray(leftNewArray, (NewArrayExpression)right), NewExpression leftNew => CompareNew(leftNew, (NewExpression)right), ParameterExpression leftParameter => CompareParameter(leftParameter, (ParameterExpression)right), RuntimeVariablesExpression leftRuntimeVariables => CompareRuntimeVariables( leftRuntimeVariables, (RuntimeVariablesExpression)right), SwitchExpression leftSwitch => CompareSwitch(leftSwitch, (SwitchExpression)right), TryExpression leftTry => CompareTry(leftTry, (TryExpression)right), TypeBinaryExpression leftTypeBinary => CompareTypeBinary(leftTypeBinary, (TypeBinaryExpression)right), UnaryExpression leftUnary => CompareUnary(leftUnary, (UnaryExpression)right), _ => left.NodeType == ExpressionType.Extension ? left.Equals(right) : throw new InvalidOperationException( $"The comparison operation has not implemented to expression type {left.NodeType}") });
// NB: This optimization takes away empty fault and finally blocks in a way similar to the C# // compiler's optimization pass. Catch handlers are left untouched. protected override Expression VisitTry(TryExpression node) { var res = base.VisitTry(node); var tryStmt = res as TryExpression; if (tryStmt != null) { // NB: It's safe to take away empty fault and finally blocks; they don't have side- // effects, don't alter exception propagation, and don't have useful properties. var @finally = tryStmt.Finally; MakeNullIfEmpty(ref @finally); var fault = tryStmt.Fault; MakeNullIfEmpty(ref fault); // NB: We obviously can't take away empty handlers; that'd cause subsequent handlers // to get considered or the exception to propagate. var handlers = tryStmt.Handlers; // NB: However, we can take away *all* handlers if we know that the body of the try // statement can't throw under any circumstance, so we check for purity below. // // Note that we *can't* take away finally or fault blocks because they can be // used for their runtime guarantees of being non-interrupted, e.g. // // try { } finally { /* critical code */ } // // This is a common pattern we shall not break by optimization of course. var body = tryStmt.Body; if (body.IsPure(true)) { handlers = null; } // NB: It's possible it all goes away, so we simply return the body in that case, which // can be a non-empty pure expression. if ((handlers == null || handlers.Count == 0) && @finally == null && fault == null) { return(body); } // NB: As long as any of { handlers, finally, fault } exists, Update is fine to morph // the original expression into a new one. return(tryStmt.Update(body, handlers, @finally, fault)); } return(res); }
protected override Expression VisitTry(TryExpression node) { if ((this.Try != null) && (node != null)) { return(base.VisitTry(this.Try(node))); } else { return(base.VisitTry(node)); } }
public static Expression WrapIntoConsoleTry(this Expression statements) { MethodInfo writeLine = typeof(Console).GetMethod("WriteLine", new[] { typeof(object) }); ParameterExpression exception = Expression.Variable(typeof(Exception)); TryExpression lambda = Expression.TryCatch(statements, Expression.Catch(exception, Expression.Call(writeLine, exception))); return(lambda); }
protected override Expression VisitTry(TryExpression node) { var res = default(Expression); if (node.Finally != null || node.Fault != null) { var body = Visit(node.Body); var handlers = Visit(node.Handlers, VisitCatchBlock); if (node.Finally != null) { Debug.Assert(node.Fault == null); var @finally = default(Expression); if (VisitAndFindAwait(node.Finally, out @finally)) { if (handlers.Count != 0) { body = Expression.TryCatch(body, handlers.ToArray()); } res = RewriteHandler(body, @finally, isFault: false); } else { res = node.Update(body, handlers, @finally, null); } } else { Debug.Assert(node.Finally == null); var fault = default(Expression); if (VisitAndFindAwait(node.Fault, out fault)) { Debug.Assert(handlers.Count == 0); res = RewriteHandler(body, fault, isFault: true); } else { res = node.Update(body, handlers, null, fault); } } } else { res = base.VisitTry(node); } return(res); }
public void FilterOnCatchInterpreted() { TryExpression tryExp = Expression.TryCatch( Expression.Throw(Expression.Constant(new TestException()), typeof(int)), Expression.Catch(typeof(TestException), Expression.Constant(1), Expression.Constant(false)), Expression.Catch(typeof(TestException), Expression.Constant(2), Expression.Constant(true)), Expression.Catch(typeof(TestException), Expression.Constant(3)) ); Assert.Equal(2, Expression.Lambda <Func <int> >(tryExp).Compile(true)()); }
public void CatchChainingInterpreted() { TryExpression chain = Expression.TryCatch( Expression.Throw(Expression.Constant(new DerivedTestException()), typeof(int)), Expression.Catch(typeof(InvalidOperationException), Expression.Constant(1)), Expression.Catch(typeof(TestException), Expression.Constant(2)), Expression.Catch(typeof(DerivedTestException), Expression.Constant(3)) ); Assert.Equal(2, Expression.Lambda <Func <int> >(chain).Compile(true)()); }
protected override ExpressionDto Visit(TryExpression expression) { return(new TryExpressionDto { NodeType = expression.NodeType, Type = expression.Type, Body = Visit(expression.Body), Fault = Visit(expression.Fault), Finally = Visit(expression.Finally), Handlers = ListSelect(expression.Handlers, GetCatchBlock) }); }
public TryExpressionProxy(TryExpression node) { _node = node; }