Browse Source

Added IResolveVisitorNavigator

newNRvisualizers
Daniel Grunwald 15 years ago
parent
commit
7d320b5da2
  1. 16
      ICSharpCode.NRefactory/CSharp/Dom/Statements/VariableDeclarationStatement.cs
  2. 29
      ICSharpCode.NRefactory/CSharp/Resolver/CSharpResolver.cs
  3. 32
      ICSharpCode.NRefactory/CSharp/Resolver/IResolveVisitorNavigator.cs
  4. 432
      ICSharpCode.NRefactory/CSharp/Resolver/ResolveVisitor.cs
  5. 1
      ICSharpCode.NRefactory/ICSharpCode.NRefactory.csproj

16
ICSharpCode.NRefactory/CSharp/Dom/Statements/VariableDeclarationStatement.cs

@ -1,6 +1,6 @@
// //
// VariableDeclarationStatement.cs // VariableDeclarationStatement.cs
// //
// Author: // Author:
// Mike Krüger <mkrueger@novell.com> // Mike Krüger <mkrueger@novell.com>
// //
@ -33,10 +33,20 @@ namespace ICSharpCode.NRefactory.CSharp
{ {
public class VariableDeclarationStatement : AbstractNode public class VariableDeclarationStatement : AbstractNode
{ {
public IEnumerable<INode> Modifiers { public IEnumerable<INode> ModifierTokens {
get { return base.GetChildrenByRole (Roles.Modifier); } get { return base.GetChildrenByRole (Roles.Modifier); }
} }
public Modifiers Modifiers {
get {
Modifiers m = 0;
foreach (CSharpModifierToken t in this.ModifierTokens) {
m |= t.Modifier;
}
return m;
}
}
public INode ReturnType { public INode ReturnType {
get { return (INode)GetChildByRole (Roles.ReturnType); } get { return (INode)GetChildByRole (Roles.ReturnType); }
} }

29
ICSharpCode.NRefactory/CSharp/Resolver/CSharpResolver.cs

@ -136,13 +136,13 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
/// <summary> /// <summary>
/// Adds a new variable to the current block. /// Adds a new variable to the current block.
/// </summary> /// </summary>
public void AddVariable(ITypeReference type, string name, IConstantValue constantValue = null) public IVariable AddVariable(ITypeReference type, string name, IConstantValue constantValue = null)
{ {
if (type == null) if (type == null)
throw new ArgumentNullException("type"); throw new ArgumentNullException("type");
if (name == null) if (name == null)
throw new ArgumentNullException("name"); throw new ArgumentNullException("name");
localVariableStack = new LocalVariable(localVariableStack, type, name, constantValue); return localVariableStack = new LocalVariable(localVariableStack, type, name, constantValue);
} }
/// <summary> /// <summary>
@ -1726,7 +1726,13 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
string newArgumentName = GuessParameterName(arguments[i]); string newArgumentName = GuessParameterName(arguments[i]);
if (argumentNames.Contains(newArgumentName)) { if (argumentNames.Contains(newArgumentName)) {
// disambiguate argument name (e.g. add a number) // disambiguate argument name (e.g. add a number)
throw new NotImplementedException(); int num = 1;
string newName;
do {
newName = newArgumentName + num.ToString();
num++;
} while(argumentNames.Contains(newArgumentName));
newArgumentName = newName;
} }
argumentNames[i] = newArgumentName; argumentNames[i] = newArgumentName;
} }
@ -1765,12 +1771,25 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
if (mgrr != null && mgrr.Methods.Count > 0) if (mgrr != null && mgrr.Methods.Count > 0)
return mgrr.Methods[0].Name; return mgrr.Methods[0].Name;
if (!string.IsNullOrEmpty(rr.Type.Name)) { VariableResolveResult vrr = rr as VariableResolveResult;
return char.ToLower(rr.Type.Name[0]) + rr.Type.Name.Substring(1); if (vrr != null)
return MakeParameterName(vrr.Variable.Name);
if (rr.Type != SharedTypes.UnknownType && !string.IsNullOrEmpty(rr.Type.Name)) {
return MakeParameterName(rr.Type.Name);
} else { } else {
return "parameter"; return "parameter";
} }
} }
static string MakeParameterName(string variableName)
{
if (string.IsNullOrEmpty(variableName))
return "parameter";
if (variableName.Length > 1 && variableName[0] == '_')
variableName = variableName.Substring(1);
return char.ToLower(variableName[0]) + variableName.Substring(1);
}
#endregion #endregion
#region ResolveIndexer #region ResolveIndexer

32
ICSharpCode.NRefactory/CSharp/Resolver/IResolveVisitorNavigator.cs

@ -0,0 +1,32 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
namespace ICSharpCode.NRefactory.CSharp.Resolver
{
public interface IResolveVisitorNavigator
{
ResolveVisitorNavigationMode Scan(INode node);
}
public enum ResolveVisitorNavigationMode
{
/// <summary>
/// Scan into the children of the current node, without resolving the current node.
/// </summary>
Scan,
/// <summary>
/// Skip the current node - do not scan into it; do not resolve it.
/// </summary>
Skip,
/// <summary>
/// Resolve the current node; but only scan subnodes which are not required for resolving the current node.
/// </summary>
Resolve,
/// <summary>
/// Resolves all nodes in the current subtree.
/// </summary>
ResolveAll
}
}

432
ICSharpCode.NRefactory/CSharp/Resolver/ResolveVisitor.cs

@ -4,14 +4,20 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
using ICSharpCode.NRefactory.TypeSystem; using ICSharpCode.NRefactory.TypeSystem;
using ICSharpCode.NRefactory.TypeSystem.Implementation; using ICSharpCode.NRefactory.TypeSystem.Implementation;
namespace ICSharpCode.NRefactory.CSharp.Resolver namespace ICSharpCode.NRefactory.CSharp.Resolver
{ {
/// <summary> /// <summary>
/// Traverses the DOM and resolves every expression. /// Traverses the DOM and resolves expressions.
/// </summary> /// </summary>
/// <remarks>
/// The ResolveVisitor does two jobs at the same time: it tracks the resolve context (properties on CSharpResolver)
/// and it resolves the expressions visited.
/// To allow using the context tracking without having to resolve every expression in the file (e.g.
/// </remarks>
public class ResolveVisitor : AbstractDomVisitor<object, ResolveResult> public class ResolveVisitor : AbstractDomVisitor<object, ResolveResult>
{ {
static readonly ResolveResult errorResult = new ErrorResolveResult(SharedTypes.UnknownType); static readonly ResolveResult errorResult = new ErrorResolveResult(SharedTypes.UnknownType);
@ -19,31 +25,81 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
readonly ParsedFile parsedFile; readonly ParsedFile parsedFile;
readonly Dictionary<INode, ResolveResult> cache = new Dictionary<INode, ResolveResult>(); readonly Dictionary<INode, ResolveResult> cache = new Dictionary<INode, ResolveResult>();
/// <summary> readonly IResolveVisitorNavigator navigator;
/// Set this property to false to skip resolving all sub expressions. ResolveVisitorNavigationMode mode = ResolveVisitorNavigationMode.Scan;
/// </summary>
public bool FullyResolveSubExpressions { get; set; } bool resolverEnabled {
get { return mode != ResolveVisitorNavigationMode.Scan; }
}
public ResolveVisitor(CSharpResolver resolver, ParsedFile parsedFile) public ResolveVisitor(CSharpResolver resolver, ParsedFile parsedFile, IResolveVisitorNavigator navigator = null)
{ {
if (resolver == null) if (resolver == null)
throw new ArgumentNullException("resolver"); throw new ArgumentNullException("resolver");
this.resolver = resolver; this.resolver = resolver;
this.parsedFile = parsedFile; this.parsedFile = parsedFile;
this.FullyResolveSubExpressions = true; this.navigator = navigator;
if (navigator == null)
mode = ResolveVisitorNavigationMode.ResolveAll;
}
#region Scan / Resolve
public void Scan(INode node, object data = null)
{
if (node == null)
return;
if (mode == ResolveVisitorNavigationMode.ResolveAll) {
Resolve(node, data);
} else {
ResolveVisitorNavigationMode oldMode = mode;
mode = navigator.Scan(node);
switch (mode) {
case ResolveVisitorNavigationMode.Skip:
break;
case ResolveVisitorNavigationMode.Scan:
node.AcceptVisitor(this, data);
break;
case ResolveVisitorNavigationMode.Resolve:
case ResolveVisitorNavigationMode.ResolveAll:
Resolve(node, data);
break;
default:
throw new Exception("Invalid value for ResolveVisitorNavigationMode");
}
mode = oldMode;
}
} }
public ResolveResult Resolve(INode node) public ResolveResult Resolve(INode node, object data = null)
{ {
if (node == null) if (node == null)
return errorResult; return errorResult;
bool wasScan = mode == ResolveVisitorNavigationMode.Scan;
if (wasScan)
mode = ResolveVisitorNavigationMode.Resolve;
ResolveResult result; ResolveResult result;
if (!cache.TryGetValue(node, out result)) { if (!cache.TryGetValue(node, out result)) {
result = cache[node] = node.AcceptVisitor(this, null) ?? errorResult; result = cache[node] = node.AcceptVisitor(this, data) ?? errorResult;
} }
if (wasScan)
mode = ResolveVisitorNavigationMode.Scan;
return result; return result;
} }
void ScanChildren(INode node)
{
for (INode child = node.FirstChild; child != null; child = child.NextSibling) {
Scan(child);
}
}
protected override ResolveResult VisitChildren(INode node, object data)
{
ScanChildren(node);
return null;
}
#endregion
public ResolveResult GetResolveResult(INode node) public ResolveResult GetResolveResult(INode node)
{ {
ResolveResult result; ResolveResult result;
@ -60,7 +116,8 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
try { try {
if (parsedFile != null) if (parsedFile != null)
resolver.UsingScope = parsedFile.RootUsingScope; resolver.UsingScope = parsedFile.RootUsingScope;
return base.VisitCompilationUnit(unit, data); ScanChildren(unit);
return null;
} finally { } finally {
resolver.UsingScope = previousUsingScope; resolver.UsingScope = previousUsingScope;
} }
@ -73,7 +130,7 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
if (parsedFile != null) { if (parsedFile != null) {
resolver.UsingScope = parsedFile.GetUsingScope(namespaceDeclaration.StartLocation); resolver.UsingScope = parsedFile.GetUsingScope(namespaceDeclaration.StartLocation);
} }
base.VisitNamespaceDeclaration(namespaceDeclaration, data); ScanChildren(namespaceDeclaration);
return new NamespaceResolveResult(resolver.UsingScope.NamespaceName); return new NamespaceResolveResult(resolver.UsingScope.NamespaceName);
} finally { } finally {
resolver.UsingScope = previousUsingScope; resolver.UsingScope = previousUsingScope;
@ -99,7 +156,7 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
} }
if (newTypeDefinition != null) if (newTypeDefinition != null)
resolver.CurrentTypeDefinition = newTypeDefinition; resolver.CurrentTypeDefinition = newTypeDefinition;
base.VisitTypeDeclaration(typeDeclaration, data); ScanChildren(typeDeclaration);
return newTypeDefinition != null ? new TypeResolveResult(newTypeDefinition) : errorResult; return newTypeDefinition != null ? new TypeResolveResult(newTypeDefinition) : errorResult;
} finally { } finally {
resolver.CurrentTypeDefinition = previousTypeDefinition; resolver.CurrentTypeDefinition = previousTypeDefinition;
@ -110,40 +167,47 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
#region Track CurrentMember #region Track CurrentMember
public override ResolveResult VisitFieldDeclaration(FieldDeclaration fieldDeclaration, object data) public override ResolveResult VisitFieldDeclaration(FieldDeclaration fieldDeclaration, object data)
{ {
if (FullyResolveSubExpressions) { int initializerCount = fieldDeclaration.Variables.Count();
ResolveType(fieldDeclaration.ReturnType); ResolveResult result = null;
foreach (AttributeSection attr in fieldDeclaration.Attributes) foreach (INode node in fieldDeclaration.Children) {
Resolve(attr); if (node.Role == FieldDeclaration.Roles.Initializer) {
} if (resolver.CurrentTypeDefinition != null) {
if (fieldDeclaration.Variables.Count() == 1) { resolver.CurrentMember = resolver.CurrentTypeDefinition.Fields.FirstOrDefault(f => f.Region.IsInside(node.StartLocation));
return Resolve(fieldDeclaration.Variables.Single()); }
} else {
foreach (VariableInitializer vi in fieldDeclaration.Variables) if (resolverEnabled && initializerCount == 1) {
Resolve(vi); result = Resolve(node);
return null; } else {
Scan(node);
}
resolver.CurrentMember = null;
} else {
Scan(node);
}
} }
return result;
} }
public override ResolveResult VisitVariableInitializer(VariableInitializer variableInitializer, object data) public override ResolveResult VisitVariableInitializer(VariableInitializer variableInitializer, object data)
{ {
if (variableInitializer.Parent is FieldDeclaration) { ScanChildren(variableInitializer);
try { if (resolverEnabled) {
if (resolver.CurrentTypeDefinition != null) { if (variableInitializer.Parent is FieldDeclaration) {
resolver.CurrentMember = resolver.CurrentTypeDefinition.Fields.FirstOrDefault(f => f.Region.IsInside(variableInitializer.StartLocation));
}
if (FullyResolveSubExpressions)
Resolve(variableInitializer.Initializer);
if (resolver.CurrentMember != null) if (resolver.CurrentMember != null)
return new MemberResolveResult(resolver.CurrentMember, resolver.CurrentMember.ReturnType.Resolve(resolver.Context)); return new MemberResolveResult(resolver.CurrentMember, resolver.CurrentMember.ReturnType.Resolve(resolver.Context));
else } else {
return errorResult; string identifier = variableInitializer.Name;
} finally{ foreach (IVariable v in resolver.LocalVariables) {
resolver.CurrentMember = null; if (v.Name == identifier) {
object constantValue = v.IsConst ? v.ConstantValue.GetValue(resolver.Context) : null;
return new VariableResolveResult(v, v.Type.Resolve(resolver.Context), constantValue);
}
}
} }
return errorResult;
} else { } else {
return base.VisitVariableInitializer(variableInitializer, data); return null;
} }
} }
@ -154,9 +218,9 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
resolver.CurrentMember = resolver.CurrentTypeDefinition.Methods.FirstOrDefault(m => m.Region.IsInside(member.StartLocation)); resolver.CurrentMember = resolver.CurrentTypeDefinition.Methods.FirstOrDefault(m => m.Region.IsInside(member.StartLocation));
} }
VisitChildren(member, data); ScanChildren(member);
if (resolver.CurrentMember != null) if (resolverEnabled && resolver.CurrentMember != null)
return new MemberResolveResult(resolver.CurrentMember, resolver.CurrentMember.ReturnType.Resolve(resolver.Context)); return new MemberResolveResult(resolver.CurrentMember, resolver.CurrentMember.ReturnType.Resolve(resolver.Context));
else else
return errorResult; return errorResult;
@ -192,23 +256,20 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
resolver.CurrentMember = resolver.CurrentTypeDefinition.Properties.FirstOrDefault(p => p.Region.IsInside(propertyDeclaration.StartLocation)); resolver.CurrentMember = resolver.CurrentTypeDefinition.Properties.FirstOrDefault(p => p.Region.IsInside(propertyDeclaration.StartLocation));
} }
if (FullyResolveSubExpressions) { foreach (INode node in propertyDeclaration.Children) {
ResolveType(propertyDeclaration.ReturnType); if (node.Role == PropertyDeclaration.PropertySetRole && resolver.CurrentMember != null) {
foreach (INode node in propertyDeclaration.GetChildrenByRole(IndexerDeclaration.Roles.Argument))
Resolve(node);
if (propertyDeclaration.GetAccessor != null)
VisitAccessorDeclaration(propertyDeclaration.GetAccessor, data);
if (propertyDeclaration.SetAccessor != null && resolver.CurrentMember != null) {
resolver.PushBlock(); resolver.PushBlock();
try { try {
resolver.AddVariable(resolver.CurrentMember.ReturnType, "value"); resolver.AddVariable(resolver.CurrentMember.ReturnType, "value");
VisitAccessorDeclaration(propertyDeclaration.SetAccessor, data); Scan(node);
} finally { } finally {
resolver.PopBlock(); resolver.PopBlock();
} }
} else {
Scan(node);
} }
} }
if (resolver.CurrentMember != null) if (resolverEnabled && resolver.CurrentMember != null)
return new MemberResolveResult(resolver.CurrentMember, resolver.CurrentMember.ReturnType.Resolve(resolver.Context)); return new MemberResolveResult(resolver.CurrentMember, resolver.CurrentMember.ReturnType.Resolve(resolver.Context));
else else
return errorResult; return errorResult;
@ -229,7 +290,12 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
bool oldCheckForOverflow = resolver.CheckForOverflow; bool oldCheckForOverflow = resolver.CheckForOverflow;
try { try {
resolver.CheckForOverflow = true; resolver.CheckForOverflow = true;
return checkedExpression.Expression.AcceptVisitor(this, data); if (resolverEnabled) {
return Resolve(checkedExpression.Expression);
} else {
ScanChildren(checkedExpression);
return null;
}
} finally { } finally {
resolver.CheckForOverflow = oldCheckForOverflow; resolver.CheckForOverflow = oldCheckForOverflow;
} }
@ -240,7 +306,12 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
bool oldCheckForOverflow = resolver.CheckForOverflow; bool oldCheckForOverflow = resolver.CheckForOverflow;
try { try {
resolver.CheckForOverflow = false; resolver.CheckForOverflow = false;
return uncheckedExpression.Expression.AcceptVisitor(this, data); if (resolverEnabled) {
return Resolve(uncheckedExpression.Expression);
} else {
ScanChildren(uncheckedExpression);
return null;
}
} finally { } finally {
resolver.CheckForOverflow = oldCheckForOverflow; resolver.CheckForOverflow = oldCheckForOverflow;
} }
@ -251,7 +322,8 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
bool oldCheckForOverflow = resolver.CheckForOverflow; bool oldCheckForOverflow = resolver.CheckForOverflow;
try { try {
resolver.CheckForOverflow = true; resolver.CheckForOverflow = true;
return base.VisitCheckedStatement(checkedStatement, data); ScanChildren(checkedStatement);
return null;
} finally { } finally {
resolver.CheckForOverflow = oldCheckForOverflow; resolver.CheckForOverflow = oldCheckForOverflow;
} }
@ -261,31 +333,15 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
{ {
bool oldCheckForOverflow = resolver.CheckForOverflow; bool oldCheckForOverflow = resolver.CheckForOverflow;
try { try {
resolver.CheckForOverflow = true; resolver.CheckForOverflow = false;
return base.VisitUncheckedStatement(uncheckedStatement, data); ScanChildren(uncheckedStatement);
return null;
} finally { } finally {
resolver.CheckForOverflow = oldCheckForOverflow; resolver.CheckForOverflow = oldCheckForOverflow;
} }
} }
#endregion #endregion
#region VisitChildren
protected override ResolveResult VisitChildren(INode node, object data)
{
// this method is used to iterate through all children
if (FullyResolveSubExpressions) {
INode child = node.FirstChild;
while (child != null) {
ResolveResult rr = child.AcceptVisitor (this, data);
if (rr != null)
cache[child] = rr;
child = child.NextSibling;
}
}
return null;
}
#endregion
#region Visit Expressions #region Visit Expressions
static bool IsTargetOfInvocation(INode node) static bool IsTargetOfInvocation(INode node)
{ {
@ -305,6 +361,7 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
public override ResolveResult VisitArgListExpression(ArgListExpression argListExpression, object data) public override ResolveResult VisitArgListExpression(ArgListExpression argListExpression, object data)
{ {
ScanChildren(argListExpression);
return new ResolveResult(resolver.Context.GetClass(typeof(RuntimeArgumentHandle)) ?? SharedTypes.UnknownType); return new ResolveResult(resolver.Context.GetClass(typeof(RuntimeArgumentHandle)) ?? SharedTypes.UnknownType);
} }
@ -315,61 +372,102 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
public override ResolveResult VisitAsExpression(AsExpression asExpression, object data) public override ResolveResult VisitAsExpression(AsExpression asExpression, object data)
{ {
if (FullyResolveSubExpressions) if (resolverEnabled) {
Resolve(asExpression.Expression); Scan(asExpression.Expression);
return new ResolveResult(ResolveType(asExpression.TypeReference)); return new ResolveResult(ResolveType(asExpression.TypeReference));
} else {
ScanChildren(asExpression);
return null;
}
} }
public override ResolveResult VisitAssignmentExpression(AssignmentExpression assignmentExpression, object data) public override ResolveResult VisitAssignmentExpression(AssignmentExpression assignmentExpression, object data)
{ {
ResolveResult left = Resolve(assignmentExpression.Left); if (resolverEnabled) {
if (FullyResolveSubExpressions) { ResolveResult left = Resolve(assignmentExpression.Left);
Resolve(assignmentExpression.Right); Scan(assignmentExpression.Right);
return new ResolveResult(left.Type);
} else {
ScanChildren(assignmentExpression);
return null;
} }
return new ResolveResult(left.Type);
} }
public override ResolveResult VisitBaseReferenceExpression(BaseReferenceExpression baseReferenceExpression, object data) public override ResolveResult VisitBaseReferenceExpression(BaseReferenceExpression baseReferenceExpression, object data)
{ {
return resolver.ResolveBaseReference(); if (resolverEnabled) {
return resolver.ResolveBaseReference();
} else {
ScanChildren(baseReferenceExpression);
return null;
}
} }
public override ResolveResult VisitBinaryOperatorExpression(BinaryOperatorExpression binaryOperatorExpression, object data) public override ResolveResult VisitBinaryOperatorExpression(BinaryOperatorExpression binaryOperatorExpression, object data)
{ {
ResolveResult left = Resolve(binaryOperatorExpression.Left); if (resolverEnabled) {
ResolveResult right = Resolve(binaryOperatorExpression.Right); ResolveResult left = Resolve(binaryOperatorExpression.Left);
return resolver.ResolveBinaryOperator(binaryOperatorExpression.BinaryOperatorType, left, right); ResolveResult right = Resolve(binaryOperatorExpression.Right);
return resolver.ResolveBinaryOperator(binaryOperatorExpression.BinaryOperatorType, left, right);
} else {
ScanChildren(binaryOperatorExpression);
return null;
}
} }
public override ResolveResult VisitCastExpression(CastExpression castExpression, object data) public override ResolveResult VisitCastExpression(CastExpression castExpression, object data)
{ {
return resolver.ResolveCast(ResolveType(castExpression.CastTo), Resolve(castExpression.Expression)); if (resolverEnabled) {
return resolver.ResolveCast(ResolveType(castExpression.CastTo), Resolve(castExpression.Expression));
} else {
ScanChildren(castExpression);
return null;
}
} }
public override ResolveResult VisitConditionalExpression(ConditionalExpression conditionalExpression, object data) public override ResolveResult VisitConditionalExpression(ConditionalExpression conditionalExpression, object data)
{ {
if (FullyResolveSubExpressions) if (resolverEnabled) {
Resolve(conditionalExpression.Condition); Scan(conditionalExpression.Condition);
return resolver.ResolveConditional(Resolve(conditionalExpression.TrueExpression), return resolver.ResolveConditional(Resolve(conditionalExpression.TrueExpression),
Resolve(conditionalExpression.FalseExpression)); Resolve(conditionalExpression.FalseExpression));
} else {
ScanChildren(conditionalExpression);
return null;
}
} }
public override ResolveResult VisitDefaultValueExpression(DefaultValueExpression defaultValueExpression, object data) public override ResolveResult VisitDefaultValueExpression(DefaultValueExpression defaultValueExpression, object data)
{ {
return new ConstantResolveResult(ResolveType(defaultValueExpression.TypeReference), null); if (resolverEnabled) {
return new ConstantResolveResult(ResolveType(defaultValueExpression.TypeReference), null);
} else {
ScanChildren(defaultValueExpression);
return null;
}
} }
public override ResolveResult VisitDirectionExpression(DirectionExpression directionExpression, object data) public override ResolveResult VisitDirectionExpression(DirectionExpression directionExpression, object data)
{ {
ResolveResult rr = Resolve(directionExpression.Expression); if (resolverEnabled) {
return new ByReferenceResolveResult(rr.Type, directionExpression.FieldDirection == FieldDirection.Out); ResolveResult rr = Resolve(directionExpression.Expression);
return new ByReferenceResolveResult(rr.Type, directionExpression.FieldDirection == FieldDirection.Out);
} else {
ScanChildren(directionExpression);
return null;
}
} }
public override ResolveResult VisitIdentifierExpression(IdentifierExpression identifierExpression, object data) public override ResolveResult VisitIdentifierExpression(IdentifierExpression identifierExpression, object data)
{ {
// TODO: type arguments? if (resolverEnabled) {
return resolver.ResolveSimpleName(identifierExpression.Identifier, EmptyList<IType>.Instance, // TODO: type arguments?
IsTargetOfInvocation(identifierExpression)); return resolver.ResolveSimpleName(identifierExpression.Identifier, EmptyList<IType>.Instance,
IsTargetOfInvocation(identifierExpression));
} else {
ScanChildren(identifierExpression);
return null;
}
} }
ResolveResult[] GetArguments(IEnumerable<INode> argumentExpressions, out string[] argumentNames) ResolveResult[] GetArguments(IEnumerable<INode> argumentExpressions, out string[] argumentNames)
@ -385,26 +483,33 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
public override ResolveResult VisitIndexerExpression(IndexerExpression indexerExpression, object data) public override ResolveResult VisitIndexerExpression(IndexerExpression indexerExpression, object data)
{ {
ResolveResult target = Resolve(indexerExpression.Target); if (resolverEnabled) {
string[] argumentNames; ResolveResult target = Resolve(indexerExpression.Target);
ResolveResult[] arguments = GetArguments(indexerExpression.Arguments, out argumentNames); string[] argumentNames;
return resolver.ResolveIndexer(target, arguments, argumentNames); ResolveResult[] arguments = GetArguments(indexerExpression.Arguments, out argumentNames);
return resolver.ResolveIndexer(target, arguments, argumentNames);
} else {
ScanChildren(indexerExpression);
return null;
}
} }
public override ResolveResult VisitInvocationExpression(InvocationExpression invocationExpression, object data) public override ResolveResult VisitInvocationExpression(InvocationExpression invocationExpression, object data)
{ {
ResolveResult target = Resolve(invocationExpression.Target); if (resolverEnabled) {
string[] argumentNames; ResolveResult target = Resolve(invocationExpression.Target);
ResolveResult[] arguments = GetArguments(invocationExpression.Arguments, out argumentNames); string[] argumentNames;
return resolver.ResolveInvocation(target, arguments, argumentNames); ResolveResult[] arguments = GetArguments(invocationExpression.Arguments, out argumentNames);
return resolver.ResolveInvocation(target, arguments, argumentNames);
} else {
ScanChildren(invocationExpression);
return null;
}
} }
public override ResolveResult VisitIsExpression(IsExpression isExpression, object data) public override ResolveResult VisitIsExpression(IsExpression isExpression, object data)
{ {
if (FullyResolveSubExpressions) { ScanChildren(isExpression);
Resolve(isExpression.Expression);
ResolveType(isExpression.TypeReference);
}
return new ResolveResult(TypeCode.Boolean.ToTypeReference().Resolve(resolver.Context)); return new ResolveResult(TypeCode.Boolean.ToTypeReference().Resolve(resolver.Context));
} }
@ -415,12 +520,17 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
public override ResolveResult VisitMemberReferenceExpression(MemberReferenceExpression memberReferenceExpression, object data) public override ResolveResult VisitMemberReferenceExpression(MemberReferenceExpression memberReferenceExpression, object data)
{ {
ResolveResult target = Resolve(memberReferenceExpression.Target); if (resolverEnabled) {
List<INode> typeArgumentNodes = memberReferenceExpression.TypeArguments.ToList(); ResolveResult target = Resolve(memberReferenceExpression.Target);
// TODO: type arguments? List<INode> typeArgumentNodes = memberReferenceExpression.TypeArguments.ToList();
return resolver.ResolveMemberAccess(target, memberReferenceExpression.MemberName, // TODO: type arguments?
EmptyList<IType>.Instance, return resolver.ResolveMemberAccess(target, memberReferenceExpression.MemberName,
IsTargetOfInvocation(memberReferenceExpression)); EmptyList<IType>.Instance,
IsTargetOfInvocation(memberReferenceExpression));
} else {
ScanChildren(memberReferenceExpression);
return null;
}
} }
public override ResolveResult VisitNullReferenceExpression(NullReferenceExpression nullReferenceExpression, object data) public override ResolveResult VisitNullReferenceExpression(NullReferenceExpression nullReferenceExpression, object data)
@ -430,15 +540,25 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
public override ResolveResult VisitObjectCreateExpression(ObjectCreateExpression objectCreateExpression, object data) public override ResolveResult VisitObjectCreateExpression(ObjectCreateExpression objectCreateExpression, object data)
{ {
IType type = ResolveType(objectCreateExpression.Type); if (resolverEnabled) {
string[] argumentNames; IType type = ResolveType(objectCreateExpression.Type);
ResolveResult[] arguments = GetArguments(objectCreateExpression.Arguments, out argumentNames); string[] argumentNames;
return resolver.ResolveObjectCreation(type, arguments, argumentNames); ResolveResult[] arguments = GetArguments(objectCreateExpression.Arguments, out argumentNames);
return resolver.ResolveObjectCreation(type, arguments, argumentNames);
} else {
ScanChildren(objectCreateExpression);
return null;
}
} }
public override ResolveResult VisitParenthesizedExpression(ParenthesizedExpression parenthesizedExpression, object data) public override ResolveResult VisitParenthesizedExpression(ParenthesizedExpression parenthesizedExpression, object data)
{ {
return Resolve(parenthesizedExpression.Expression); if (resolverEnabled) {
return Resolve(parenthesizedExpression.Expression);
} else {
Scan(parenthesizedExpression.Expression);
return null;
}
} }
public override ResolveResult VisitPointerReferenceExpression(PointerReferenceExpression pointerReferenceExpression, object data) public override ResolveResult VisitPointerReferenceExpression(PointerReferenceExpression pointerReferenceExpression, object data)
@ -453,14 +573,23 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
public override ResolveResult VisitSizeOfExpression(SizeOfExpression sizeOfExpression, object data) public override ResolveResult VisitSizeOfExpression(SizeOfExpression sizeOfExpression, object data)
{ {
return resolver.ResolveSizeOf(ResolveType(sizeOfExpression.Type)); if (resolverEnabled) {
return resolver.ResolveSizeOf(ResolveType(sizeOfExpression.Type));
} else {
ScanChildren(sizeOfExpression);
return null;
}
} }
public override ResolveResult VisitStackAllocExpression(StackAllocExpression stackAllocExpression, object data) public override ResolveResult VisitStackAllocExpression(StackAllocExpression stackAllocExpression, object data)
{ {
if (FullyResolveSubExpressions) if (resolverEnabled) {
Resolve(stackAllocExpression.CountExpression); Scan(stackAllocExpression.CountExpression);
return new ResolveResult(new PointerType(ResolveType(stackAllocExpression.Type))); return new ResolveResult(new PointerType(ResolveType(stackAllocExpression.Type)));
} else {
ScanChildren(stackAllocExpression);
return null;
}
} }
public override ResolveResult VisitThisReferenceExpression(ThisReferenceExpression thisReferenceExpression, object data) public override ResolveResult VisitThisReferenceExpression(ThisReferenceExpression thisReferenceExpression, object data)
@ -472,43 +601,70 @@ namespace ICSharpCode.NRefactory.CSharp.Resolver
public override ResolveResult VisitTypeOfExpression(TypeOfExpression typeOfExpression, object data) public override ResolveResult VisitTypeOfExpression(TypeOfExpression typeOfExpression, object data)
{ {
if (FullyResolveSubExpressions) ScanChildren(typeOfExpression);
ResolveType(typeOfExpression.Type); if (resolverEnabled)
return new ResolveResult(systemType.Resolve(resolver.Context)); return new ResolveResult(systemType.Resolve(resolver.Context));
else
return null;
} }
public override ResolveResult VisitUnaryOperatorExpression(UnaryOperatorExpression unaryOperatorExpression, object data) public override ResolveResult VisitUnaryOperatorExpression(UnaryOperatorExpression unaryOperatorExpression, object data)
{ {
ResolveResult expr = Resolve(unaryOperatorExpression.Expression); if (resolverEnabled) {
return resolver.ResolveUnaryOperator(unaryOperatorExpression.UnaryOperatorType, expr); ResolveResult expr = Resolve(unaryOperatorExpression.Expression);
return resolver.ResolveUnaryOperator(unaryOperatorExpression.UnaryOperatorType, expr);
} else {
ScanChildren(unaryOperatorExpression);
return null;
}
} }
#endregion #endregion
public override ResolveResult VisitBlockStatement(BlockStatement blockStatement, object data) public override ResolveResult VisitBlockStatement(BlockStatement blockStatement, object data)
{ {
resolver.PushBlock(); resolver.PushBlock();
try { ScanChildren(blockStatement);
return base.VisitBlockStatement(blockStatement, data); resolver.PopBlock();
} finally { return null;
resolver.PopBlock(); }
public override ResolveResult VisitVariableDeclarationStatement(VariableDeclarationStatement variableDeclarationStatement, object data)
{
IType type = ResolveType(variableDeclarationStatement.ReturnType);
if (variableDeclarationStatement.Variables.Count() == 1) {
if (type == SharedTypes.UnknownType && IsVar(variableDeclarationStatement.ReturnType)) {
ResolveResult rr = Resolve(variableDeclarationStatement.Variables.Single().Initializer);
type = rr.Type;
}
return Resolve(variableDeclarationStatement.Variables.Single(), type);
} else {
foreach (VariableInitializer vi in variableDeclarationStatement.Variables)
Resolve(vi, type);
return null;
} }
} }
bool IsVar(INode returnType)
{
return returnType is IdentifierExpression && ((IdentifierExpression)returnType).Identifier == "var";
}
public override ResolveResult VisitParameterDeclaration(ParameterDeclaration parameterDeclaration, object data) public override ResolveResult VisitParameterDeclaration(ParameterDeclaration parameterDeclaration, object data)
{ {
if (FullyResolveSubExpressions) { ScanChildren(parameterDeclaration);
ResolveType(parameterDeclaration.Type); if (resolverEnabled) {
Resolve(parameterDeclaration.DefaultExpression); IParameterizedMember pm = resolver.CurrentMember as IParameterizedMember;
} if (pm != null) {
IParameterizedMember pm = resolver.CurrentMember as IParameterizedMember; foreach (IParameter p in pm.Parameters) {
if (pm != null) { if (p.Name == parameterDeclaration.Name) {
foreach (IParameter p in pm.Parameters) { return new VariableResolveResult(p, p.Type.Resolve(resolver.Context));
if (p.Name == parameterDeclaration.Name) { }
return new VariableResolveResult(p, p.Type.Resolve(resolver.Context));
} }
} }
return errorResult;
} else {
return null;
} }
return errorResult;
} }
} }
} }

1
ICSharpCode.NRefactory/ICSharpCode.NRefactory.csproj

@ -165,6 +165,7 @@
<Compile Include="CSharp\Resolver\Conversions.cs" /> <Compile Include="CSharp\Resolver\Conversions.cs" />
<Compile Include="CSharp\Resolver\CSharpResolver.cs" /> <Compile Include="CSharp\Resolver\CSharpResolver.cs" />
<Compile Include="CSharp\Resolver\ErrorResolveResult.cs" /> <Compile Include="CSharp\Resolver\ErrorResolveResult.cs" />
<Compile Include="CSharp\Resolver\IResolveVisitorNavigator.cs" />
<Compile Include="CSharp\Resolver\ITypeOrNamespaceReference.cs" /> <Compile Include="CSharp\Resolver\ITypeOrNamespaceReference.cs" />
<Compile Include="CSharp\Resolver\MemberLookup.cs" /> <Compile Include="CSharp\Resolver\MemberLookup.cs" />
<Compile Include="CSharp\Resolver\MemberResolveResult.cs" /> <Compile Include="CSharp\Resolver\MemberResolveResult.cs" />

Loading…
Cancel
Save