IEnumerable <EntityNode> FindTypeUsage(TypeDef type) { if (type == null) { yield break; } if (type == analyzedType) { yield break; } if (IsUsedInTypeDef(type)) { yield return new TypeNode(type) { Context = Context } } ; foreach (var field in type.Fields.Where(IsUsedInFieldRef)) { yield return new FieldNode(field) { Context = Context } } ; foreach (var method in type.Methods) { SourceRef?sourceRef = null; if (IsUsedInMethodDef(method, ref sourceRef)) { yield return(HandleSpecialMethodNode(method, sourceRef)); } } } EntityNode HandleSpecialMethodNode(MethodDef method, SourceRef?sourceRef) { var property = method.DeclaringType.Properties.FirstOrDefault(p => p.GetMethod == method || p.SetMethod == method); if (property != null) { return new PropertyNode(property) { Context = Context, SourceRef = sourceRef } } ; return(new MethodNode(method) { Context = Context, SourceRef = sourceRef }); } bool IsUsedInTypeRefs(IEnumerable <ITypeDefOrRef> types) => types.Any(IsUsedInTypeRef); bool IsUsedInTypeRef(ITypeDefOrRef type) { if (type == null) { return(false); } return(TypeMatches(type.DeclaringType) || TypeMatches(type)); } bool IsUsedInTypeDef(TypeDef type) { if (type == null) { return(false); } return(IsUsedInTypeRef(type) || TypeMatches(type.BaseType) || IsUsedInTypeRefs(type.Interfaces.Select(ii => ii.Interface))); } bool IsUsedInFieldRef(IField field) { if (field == null || !field.IsField) { return(false); } return(TypeMatches(field.DeclaringType) || TypeMatches(field.FieldSig.GetFieldType())); } bool IsUsedInMethodRef(IMethod method) { if (method == null || !method.IsMethod) { return(false); } return(TypeMatches(method.DeclaringType) || TypeMatches(method.MethodSig.GetRetType()) || IsUsedInMethodParameters(method.GetParameters())); } bool IsUsedInMethodDef(MethodDef method, ref SourceRef?sourceRef) => IsUsedInMethodRef(method) || IsUsedInMethodBody(method, ref sourceRef); bool IsUsedInMethodBody(MethodDef method, ref SourceRef?sourceRef) { if (method == null) { return(false); } if (method.Body == null) { return(false); } foreach (var instruction in method.Body.Instructions) { ITypeDefOrRef tr = instruction.Operand as ITypeDefOrRef; if (IsUsedInTypeRef(tr)) { sourceRef = new SourceRef(method, instruction.Offset, instruction.Operand as IMDTokenProvider); return(true); } IField fr = instruction.Operand as IField; if (IsUsedInFieldRef(fr)) { sourceRef = new SourceRef(method, instruction.Offset, instruction.Operand as IMDTokenProvider); return(true); } IMethod mr = instruction.Operand as IMethod; if (IsUsedInMethodRef(mr)) { sourceRef = new SourceRef(method, instruction.Offset, instruction.Operand as IMDTokenProvider); return(true); } } return(false); } bool IsUsedInMethodParameters(IEnumerable <Parameter> parameters) => parameters.Any(IsUsedInMethodParameter); bool IsUsedInMethodParameter(Parameter parameter) => !parameter.IsHiddenThisParameter && TypeMatches(parameter.Type); bool TypeMatches(IType tref) => tref != null && new SigComparer().Equals(analyzedType, tref);
public DefRef(T def, SourceRef sourceRef) { this.Def = def; this.SourceRef = sourceRef; }
public DefRef(T def, SourceRef sourceRef) { Def = def; SourceRef = sourceRef; }