private void ValidateGetTypeExpression(MethodInfo validatedMethod, IExpression expression) { IMethodCallExpression callExpression = expression as IMethodCallExpression; if (callExpression == null) { return; } if (callExpression.Method != typeof(object).GetMethod("GetType")) { return; } IExpression instanceExpression = callExpression.Instance; Type type = instanceExpression.ReturnType; if (type == null) { return; } if (!type.GetCustomAttributes(typeof(FileExtensionAttribute)).Any()) { MessageSource.MessageSink.Write( new Message( MessageLocation.Of(this.userMethod), SeverityType.Error, "MYERR1", String.Format("Calling method {0} on type {1} is not allowed.", validatedMethod, type), null, null, null ) ); } }
/// <summary> /// Visits a method call. /// </summary> /// <param name="expression"></param> /// <returns></returns> public override object VisitMethodCallExpression(IMethodCallExpression expression) { if (expression.Method == _parameter.Member) { // We are inspecting the call to the method of interest. IExpression argument = expression.Arguments[_parameter.Position]; var constantExpression = argument as IConstantExpression; if (constantExpression != null) { string resourceName = (string)constantExpression.Value; if (_resourceManager.GetString(resourceName) == null) { // Write a warning. Message.Write(expression.ParentMethodBody.Method, SeverityType.Warning, "VRN04", "The string \"{0}\" in method {1} is not a valid resource name.", resourceName, expression.Method); } } } return(base.VisitMethodCallExpression(expression)); }
public override object VisitMethodCallExpression(IMethodCallExpression expression) { // check if analysis of this property isn't terminated if (this.context.Current.PropertyAnalysisTerminated) { return(expression); } string invocationPath; // if expression is property invocation chain add explicate dependency and don't analyze this branch. if (this.context.Current.IsInCurrentProperty() && this.TryGetPropertyInvocationChain(expression, out invocationPath)) { this.context.Current.ExplicitDependencyMap.AddDependency(this.context.Current.CurrentProperty.Name, invocationPath); return(base.VisitMethodCallExpression(expression)); } List <string> ivocationPaths; // if expression is Depends.On call add explicit dependency and terminate analysis of this property if (this.TryGetDependsOn(expression, out ivocationPaths)) { // Depends.On is valid only in property if (this.context.Current.Parent == null || !this.context.Current.Parent.IsInCurrentProperty()) { DomainMessageSource.Instance.Write( this.context.Current.CurrentProperty, SeverityType.Error, "DOM012", this.context.Current.CurrentMethod); } this.context.Current.TerminateCurrentPropertyAnalysis(); this.context.Current.ExplicitDependencyMap.AddDependencies(this.context.Current.CurrentProperty.Name, ivocationPaths); return(expression); } ExpressionValidationResult validationResult = this.context.Current.Validate(expression); if (validationResult.HasFlag(ExpressionValidationResult.ImmediateReturn)) { return(base.VisitMethodCallExpression(expression)); } this.AnalyzeMethodRecursive(expression.Method); IList <FieldInfo> calledMethodFields; this.methodFieldDependencies.TryGetValue(expression.Method, out calledMethodFields); if (calledMethodFields != null) { IList <FieldInfo> fieldList = this.methodFieldDependencies.GetOrCreate(this.context.Current.CurrentMethod, () => new List <FieldInfo>()); foreach (FieldInfo calledMethodField in calledMethodFields) { fieldList.AddIfNew(calledMethodField); } } return(base.VisitMethodCallExpression(expression)); }
public virtual void VisitMethodCallExpression <TExpression, TArgument>( IMethodCallExpression <TExpression, TArgument> methodCallExpression) where TExpression : IGenericExpression where TArgument : IArgument { Visit(methodCallExpression); }
public ExpressionValidationResultWithErrors ValidateMethod(IMethodCallExpression methodCallExpression, AnalysisContext currentContext) { MethodInfo methodInfo = methodCallExpression.Method as MethodInfo; if (methodInfo == null) { return(ExpressionValidationResultWithErrors.Abstain); } bool allargumentsAreIntrinsic = methodCallExpression.Arguments.All(e => e.ReturnType.IsIntrinsic() || e.ReturnType.IsIntrinsicOrObjectArray()); if (methodInfo.IsIdempotentMethod() && allargumentsAreIntrinsic) { return(ExpressionValidationResultWithErrors.AcceptImidietReturn); } if ((methodCallExpression.Instance == null || methodCallExpression.Instance.SyntaxElementKind != SyntaxElementKind.This) && (methodInfo.IsFrameworkStaticMethod() && allargumentsAreIntrinsic)) { return(ExpressionValidationResultWithErrors.AcceptImidietReturn); } return(ExpressionValidationResultWithErrors.Abstain); }
public static void VisitMethodCallExpressionChildren<TExpression, TArgument>( IMethodCallExpression<TExpression, TArgument> methodCallExpression, IGenericExpressionVisitor visitor) where TExpression : IGenericExpression where TArgument : IArgument { GenericExpressionChildVisitor.VisitMethodCallExpressionChildren<IMethodCallExpression<TExpression, TArgument>, TExpression, TArgument, IGenericExpressionVisitor>(methodCallExpression, visitor); }
public override void VisitMethodCallExpression <TExpression, TArgument>( IMethodCallExpression <TExpression, TArgument> methodCallExpression) { Steps.Add(new WriteExpression <TExpression>(methodCallExpression.Expression)); Steps.Add(new WriteStartParenthesis()); Steps.AddCommaSeparatedExpressionSteps(methodCallExpression.Parameters); Steps.Add(new WriteEndParenthesis()); }
public override void VisitMethodCallExpression <TExpression, TArgument>( IMethodCallExpression <TExpression, TArgument> methodCallExpression) { Value = new Expression() { MethodCallExpression = new MethodCallExpressionFactory(methodCallExpression).Value }; }
public override object VisitMethodCallExpression(IMethodCallExpression expression) { foreach (MethodInfo validatedMethod in this.validatedMethods) { if (validatedMethod != expression.Method) { continue; } this.ValidateTypeOfExpression(validatedMethod, expression.Arguments[0]); this.ValidateGetTypeExpression(validatedMethod, expression.Arguments[0]); } return(base.VisitMethodCallExpression(expression)); }
public void collectFromMethodCall(IMethodCallExpression methodCall) { if (methodCall.typeArgs.length() == 0) { return; } if (methodCall.typeArgs.length() != methodCall.method.typeArguments.length()) { throw new Error($"Expected {methodCall.method.typeArguments.length()} type argument(s) for method call, but got {methodCall.typeArgs.length()}"); } for (int i = 0; i < methodCall.typeArgs.length(); i++) { this.addResolution(methodCall.method.typeArguments.get(i), methodCall.typeArgs.get(i)); } }
private bool TryGetPropertyInvocationChain(IExpression expression, out string invocationPath) { invocationPath = null; Stack <string> invocationStack = new Stack <string>(); IExpression currentExpression = expression; while ((currentExpression is IMethodCallExpression && currentExpression.SyntaxElementKind != SyntaxElementKind.This) || currentExpression.SyntaxElementKind == SyntaxElementKind.Box) { if (currentExpression.SyntaxElementKind == SyntaxElementKind.Box) { currentExpression = (currentExpression as IUnaryExpression).Value; } else { IMethodCallExpression methodCallExpression = (IMethodCallExpression)currentExpression; if (!(methodCallExpression.Method.IsSpecialName && methodCallExpression.Method.Name.StartsWith("get_"))) { return(false); } invocationStack.Push(((IMethodCallExpression)currentExpression).Method.Name.Substring(4)); currentExpression = methodCallExpression.Instance; } } if (currentExpression == null || (currentExpression.SyntaxElementKind != SyntaxElementKind.This && currentExpression.SyntaxElementKind != SyntaxElementKind.Field)) { return(false); } IFieldExpression fieldExpression = currentExpression as IFieldExpression; if (fieldExpression != null) { invocationStack.Push(fieldExpression.Field.Name); } invocationPath = invocationStack.Aggregate(new StringBuilder(), (builder, s) => builder.Append('.').Append(s)).Remove(0, 1).ToString(); return(true); }
public ExpressionValidationResult Validate(IExpression expression, AnalysisContext currentContext) { IMethodCallExpression methodCallExpression = expression as IMethodCallExpression; if (methodCallExpression != null) { return(this.ProcessResults( this.methodCallValidators.Select(v => v.ValidateMethod(methodCallExpression, currentContext)), currentContext)); } IFieldExpression fieldExpression = expression as IFieldExpression; if (fieldExpression != null) { return(this.ProcessResults(this.fieldValidators.Select(v => v.ValidateField(fieldExpression, currentContext)), currentContext)); } return(ExpressionValidationResult.Abstain); }
public ExpressionValidationResultWithErrors ValidateMethod(IMethodCallExpression methodCallExpression, AnalysisContext currentContext) { if (methodCallExpression.Method.IsVirtual) { if (!currentContext.IsNotifyPropertyChangedSafeProperty) { return(new ExpressionValidationResultWithErrors(ExpressionValidationResult.RejectImmediateReturn) { MessageId = "DOM011", SeverityType = SeverityType.Error, MessageArguments = new object[] { currentContext.CurrentProperty, currentContext.CurrentMethod } }); } return(ExpressionValidationResultWithErrors.AcceptImidietReturn); } return(ExpressionValidationResultWithErrors.Abstain); }
public ExpressionValidationResultWithErrors ValidateMethod(IMethodCallExpression methodCallExpression, AnalysisContext currentContext) { MethodInfo methodInfo = methodCallExpression.Method as MethodInfo; if (methodInfo == null) { return(ExpressionValidationResultWithErrors.Abstain); } foreach (Func <MethodInfo, bool> predicate in this.predicates) { if (predicate(methodInfo)) { return(ExpressionValidationResultWithErrors.AcceptImidietReturn); } } return(ExpressionValidationResultWithErrors.Abstain); }
private bool TryGetDependsOn(IMethodCallExpression expression, out List <string> invocationPaths) { MethodInfo methodInfo = (MethodInfo)expression.Method; invocationPaths = new List <string>(); if (methodInfo.Name != "On" || methodInfo.DeclaringType != typeof(Depends)) { return(false); } foreach (IExpression exp in expression.Arguments) { string invocationPath; if (this.TryGetPropertyInvocationChain(exp, out invocationPath)) { invocationPaths.Add(invocationPath); } } return(true); }
public override object VisitMethodCallExpression(IMethodCallExpression expression) { if (expression.Method == weakEvent.AddMethod) { var newObjectExpression = expression.Arguments[0] as INewObjectExpression; if (newObjectExpression != null) { var methodPointerExpression = newObjectExpression.Arguments[1] as IMethodPointerExpression; if (methodPointerExpression != null) { var eventClientType = methodPointerExpression.Method.DeclaringType; if (!typeof(IWeakEventClient).IsAssignableFrom(eventClientType) && !HasWeakEventClientAspect(eventClientType)) { Message.Write(eventClientType, SeverityType.Error, "WEAKEVENT", "The type {0} should have the [WeakEventClient] aspect.", eventClientType); } } } } return(base.VisitMethodCallExpression(expression)); }
public ExpressionValidationResultWithErrors ValidateMethod(IMethodCallExpression methodCallExpression, AnalysisContext currentContext) { if (methodCallExpression.Instance == null || methodCallExpression.Instance.SyntaxElementKind != SyntaxElementKind.This) { // emit error only fi we are not in NotifyPropertyChangedSafeProperty if (!currentContext.IsNotifyPropertyChangedSafeProperty) { // Method contains call to non void (ref/out param) method of another class. return(new ExpressionValidationResultWithErrors(ExpressionValidationResult.RejectImmediateReturn) { MessageId = "DOM002", SeverityType = SeverityType.Error, MessageArguments = new object[] { currentContext.CurrentProperty, currentContext.CurrentMethod } }); } return(ExpressionValidationResultWithErrors.AcceptImidietReturn); } return(ExpressionValidationResultWithErrors.Abstain); }
private void ValidateTypeOfExpression(MethodInfo validatedMethod, IExpression expression) { IMethodCallExpression callExpression = expression as IMethodCallExpression; if (callExpression == null) { return; } if (callExpression.Method != typeof(Type).GetMethod("GetTypeFromHandle")) { return; } IMetadataExpression metadataExpression = callExpression.Arguments[0] as IMetadataExpression; if (metadataExpression == null) { return; } Type type = metadataExpression.Declaration as Type; if (type == null) { return; } if (!type.GetCustomAttributes(typeof(FileExtensionAttribute)).Any()) { MessageSource.MessageSink.Write( new Message( MessageLocation.Of(this.userMethod), SeverityType.Error, "MYERR1", String.Format("Calling method {0} on type {1} is not allowed.", validatedMethod, type), null, null, null ) ); } }
protected void resolveReturnType(IMethodCallExpression expr, GenericsResolver genericsResolver) { genericsResolver.collectFromMethodCall(expr); for (int i = 0; i < expr.args.length(); i++) { // actually doesn't have to resolve, but must check if generic type confirm the previous argument with the same generic type var paramType = genericsResolver.resolveType(expr.method.parameters.get(i).type, false); if (paramType != null) { expr.args.get(i).setExpectedType(paramType); } expr.args.set(i, this.main.runPluginsOn(expr.args.get(i))); genericsResolver.collectResolutionsFromActualType(paramType, expr.args.get(i).actualType); } if (expr.method.returns == null) { this.errorMan.throw_($"Method ({expr.method.parentInterface.name}::{expr.method.name}) return type was not specified or infered before the call."); return; } expr.setActualType(genericsResolver.resolveType(expr.method.returns, true), true, expr is InstanceMethodCallExpression instMethCallExpr && TypeHelper.isGeneric(instMethCallExpr.object_.getType())); }
public ExpressionValidationResultWithErrors ValidateMethod( IMethodCallExpression methodCallExpression, AnalysisContext currentContext ) { if ( methodCallExpression.Instance == null || methodCallExpression.Instance.SyntaxElementKind != SyntaxElementKind.This ) { // emit error only fi we are not in NotifyPropertyChangedSafeProperty if ( !currentContext.IsNotifyPropertyChangedSafeProperty ) { // Method contains call to non void (ref/out param) method of another class. return new ExpressionValidationResultWithErrors( ExpressionValidationResult.RejectImmediateReturn ) { MessageId = "DOM002", SeverityType = SeverityType.Error, MessageArguments = new object[] { currentContext.CurrentProperty, currentContext.CurrentMethod } }; } return ExpressionValidationResultWithErrors.AcceptImidietReturn; } return ExpressionValidationResultWithErrors.Abstain; }
public ExpressionValidationResultWithErrors ValidateMethod( IMethodCallExpression methodCallExpression, AnalysisContext currentContext ) { MethodInfo methodInfo = methodCallExpression.Method as MethodInfo; if ( methodInfo == null ) { return ExpressionValidationResultWithErrors.Abstain; } bool allargumentsAreIntrinsic = methodCallExpression.Arguments.All( e => e.ReturnType.IsIntrinsic() || e.ReturnType.IsIntrinsicOrObjectArray() ); if ( methodInfo.IsIdempotentMethod() && allargumentsAreIntrinsic ) { return ExpressionValidationResultWithErrors.AcceptImidietReturn; } if ( (methodCallExpression.Instance == null || methodCallExpression.Instance.SyntaxElementKind != SyntaxElementKind.This) && (methodInfo.IsFrameworkStaticMethod() && allargumentsAreIntrinsic) ) { return ExpressionValidationResultWithErrors.AcceptImidietReturn; } return ExpressionValidationResultWithErrors.Abstain; }
private bool TryGetDependsOn( IMethodCallExpression expression, out List<string> invocationPaths ) { MethodInfo methodInfo = (MethodInfo)expression.Method; invocationPaths = new List<string>(); if ( methodInfo.Name != "On" || methodInfo.DeclaringType != typeof(Depends) ) { return false; } foreach ( IExpression exp in expression.Arguments ) { string invocationPath; if ( this.TryGetPropertyInvocationChain( exp, out invocationPath ) ) { invocationPaths.Add( invocationPath ); } } return true; }
public override object VisitMethodCallExpression( IMethodCallExpression expression ) { // check if analysis of this property isn't terminated if ( this.context.Current.PropertyAnalysisTerminated ) { return expression; } string invocationPath; // if expression is property invocation chain add explicate dependency and don't analyze this branch. if ( this.context.Current.IsInCurrentProperty() && this.TryGetPropertyInvocationChain( expression, out invocationPath ) ) { this.context.Current.ExplicitDependencyMap.AddDependency( this.context.Current.CurrentProperty.Name, invocationPath ); return base.VisitMethodCallExpression( expression ); } List<string> ivocationPaths; // if expression is Depends.On call add explicit dependency and terminate analysis of this property if ( this.TryGetDependsOn( expression, out ivocationPaths ) ) { // Depends.On is valid only in property if ( this.context.Current.Parent == null || !this.context.Current.Parent.IsInCurrentProperty() ) { DomainMessageSource.Instance.Write( this.context.Current.CurrentProperty, SeverityType.Error, "DOM012", this.context.Current.CurrentMethod ); } this.context.Current.TerminateCurrentPropertyAnalysis(); this.context.Current.ExplicitDependencyMap.AddDependencies( this.context.Current.CurrentProperty.Name, ivocationPaths ); return expression; } ExpressionValidationResult validationResult = this.context.Current.Validate( expression ); if ( validationResult.HasFlag( ExpressionValidationResult.ImmediateReturn ) ) { return base.VisitMethodCallExpression( expression ); } this.AnalyzeMethodRecursive( expression.Method ); IList<FieldInfo> calledMethodFields; this.methodFieldDependencies.TryGetValue( expression.Method, out calledMethodFields ); if ( calledMethodFields != null ) { IList<FieldInfo> fieldList = this.methodFieldDependencies.GetOrCreate( this.context.Current.CurrentMethod, () => new List<FieldInfo>() ); foreach ( FieldInfo calledMethodField in calledMethodFields ) { fieldList.AddIfNew( calledMethodField ); } } return base.VisitMethodCallExpression( expression ); }
public ExpressionValidationResultWithErrors ValidateMethod( IMethodCallExpression methodCallExpression, AnalysisContext currentContext ) { MethodInfo methodInfo = methodCallExpression.Method as MethodInfo; if ( methodInfo == null ) { return ExpressionValidationResultWithErrors.Abstain; } foreach ( Func<MethodInfo, bool> predicate in this.predicates ) { if ( predicate( methodInfo ) ) { return ExpressionValidationResultWithErrors.AcceptImidietReturn; } } return ExpressionValidationResultWithErrors.Abstain; }
public ExpressionValidationResultWithErrors ValidateMethod( IMethodCallExpression methodCallExpression, AnalysisContext currentContext ) { if ( methodCallExpression.Method.IsVirtual ) { if ( !currentContext.IsNotifyPropertyChangedSafeProperty ) { return new ExpressionValidationResultWithErrors( ExpressionValidationResult.RejectImmediateReturn ) { MessageId = "DOM011", SeverityType = SeverityType.Error, MessageArguments = new object[] { currentContext.CurrentProperty, currentContext.CurrentMethod } }; } return ExpressionValidationResultWithErrors.AcceptImidietReturn; } return ExpressionValidationResultWithErrors.Abstain; }