public virtual Differences VisitAssemblyReferenceList(AssemblyReferenceList list1, AssemblyReferenceList list2, out AssemblyReferenceList changes, out AssemblyReferenceList deletions, out AssemblyReferenceList insertions){ changes = list1 == null ? null : list1.Clone(); deletions = list1 == null ? null : list1.Clone(); insertions = list1 == null ? new AssemblyReferenceList() : list1.Clone(); //^ assert insertions != null; Differences differences = new Differences(); //Compare references that have matching assembly names TrivialHashtable matchingPosFor = new TrivialHashtable(); TrivialHashtable matchedNodes = new TrivialHashtable(); for (int j = 0, n = list2 == null ? 0 : list2.Count; j < n; j++){ //^ assert list2 != null; AssemblyReference nd2 = list2[j]; if (nd2 == null || nd2.Name == null) continue; matchingPosFor[Identifier.For(nd2.Name).UniqueIdKey] = j; insertions.Add(null); } for (int i = 0, n = list1 == null ? 0 : list1.Count; i < n; i++){ //^ assert list1 != null && changes != null && deletions != null; AssemblyReference nd1 = list1[i]; if (nd1 == null || nd1.Name == null) continue; object pos = matchingPosFor[Identifier.For(nd1.Name).UniqueIdKey]; if (!(pos is int)) continue; //^ assert pos != null; //^ assume list2 != null; //since there was entry int matchingPosFor int j = (int)pos; AssemblyReference nd2 = list2[j]; //^ assume nd2 != null; //nd1 and nd2 define the same alias name and are therefore treated as the same entity matchedNodes[nd1.UniqueKey] = nd1; matchedNodes[nd2.UniqueKey] = nd2; //nd1 and nd2 may still be different, though, so find out how different Differences diff = this.VisitAssemblyReference(nd1, nd2); if (diff == null){Debug.Assert(false); continue;} if (diff.NumberOfDifferences != 0){ changes[i] = diff.Changes as AssemblyReference; deletions[i] = diff.Deletions as AssemblyReference; insertions[i] = diff.Insertions as AssemblyReference; insertions[n+j] = nd1; //Records the position of nd2 in list2 in case the change involved a permutation Debug.Assert(diff.Changes == changes[i] && diff.Deletions == deletions[i] && diff.Insertions == insertions[i]); differences.NumberOfDifferences += diff.NumberOfDifferences; differences.NumberOfSimilarities += diff.NumberOfSimilarities; continue; } changes[i] = null; deletions[i] = null; insertions[i] = null; insertions[n+j] = nd1; //Records the position of nd2 in list2 in case the change involved a permutation } //Find deletions for (int i = 0, n = list1 == null ? 0 : list1.Count; i < n; i++){ //^ assert list1 != null && changes != null && deletions != null; AssemblyReference nd1 = list1[i]; if (nd1 == null) continue; if (matchedNodes[nd1.UniqueKey] != null) continue; changes[i] = null; deletions[i] = nd1; insertions[i] = null; differences.NumberOfDifferences += 1; } //Find insertions for (int j = 0, n = list1 == null ? 0 : list1.Count, m = list2 == null ? 0 : list2.Count; j < m; j++){ //^ assert list2 != null; AssemblyReference nd2 = list2[j]; if (nd2 == null) continue; if (matchedNodes[nd2.UniqueKey] != null) continue; insertions[n+j] = nd2; //Records nd2 as an insertion into list1, along with its position in list2 differences.NumberOfDifferences += 1; } if (differences.NumberOfDifferences == 0){ changes = null; deletions = null; insertions = null; } return differences; }
public virtual AssemblyReferenceList VisitAssemblyReferenceList(AssemblyReferenceList assemblyReferences, AssemblyReferenceList changes, AssemblyReferenceList deletions, AssemblyReferenceList insertions){ if (changes == null || deletions == null || insertions == null) return assemblyReferences; int n = assemblyReferences == null ? 0 : assemblyReferences.Count; if (n > changes.Count){Debug.Assert(false); n = changes.Count;} if (n > deletions.Count){Debug.Assert(false); n = deletions.Count;} if (n > insertions.Count){Debug.Assert(false); n = insertions.Count;} if (assemblyReferences != null) for (int i = 0; i < n; i++) assemblyReferences[i] = this.VisitAssemblyReference(assemblyReferences[i], changes[i], deletions[i], insertions[i]); AssemblyReferenceList result = new AssemblyReferenceList(insertions.Count-n); for (int i = n, m = insertions.Count; i < m; i++) result.Add(insertions[i]); return result; }
protected virtual void ApplyAndRemoveContractAssemblies(CompilerOptions coptions, Module module){ if (module == null) return; AssemblyReferenceList references = module.AssemblyReferences; if (references == null) return; AssemblyReferenceList keepers = new AssemblyReferenceList(); for (int i = 0; i < references.Count; i++){ AssemblyReference aref = references[i]; if (aref == null) continue; AssemblyNode contractAssem = references[i].Assembly; if (contractAssem == null) continue; if (coptions != null && coptions.NoStandardLibrary && aref.Name != null && !aref.Name.EndsWith("Contracts")) { keepers.Add(aref); continue; } AttributeNode attr = contractAssem.GetAttribute(SystemTypes.ShadowsAssemblyAttribute); if (attr == null || contractAssem.ContractAssembly != null) { keepers.Add(aref); continue; } if (attr.Expressions == null || attr.Expressions.Count < 3) continue; //Bad attribute Literal lit = attr.Expressions[0] as Literal; if (lit == null) continue; //Bad attribute string publicKeyString = lit.Value as String; if (publicKeyString == null) continue; //Bad attribute int n = publicKeyString.Length; if ((n & 1) == 1) continue; //Bad attribute byte[] publicKey = new byte[n/2]; for (int j = 0; j < n; j += 2) publicKey[j/2] = (byte)int.Parse(publicKeyString.Substring(j,2), System.Globalization.NumberStyles.HexNumber); lit = attr.Expressions[1] as Literal; if (lit == null) continue; string version = lit.Value as string; if (version == null) continue; lit = attr.Expressions[2] as Literal; if (lit == null) continue; string contractAssemName = lit.Value as string; if (contractAssemName == null) continue; Version contractVersion = null; try{ contractVersion = new Version(version); }catch{} if (contractVersion == null) continue; AssemblyNode matchesExceptForVersion = null; AssemblyNode exactMatch = null; for (int j = 0; j < references.Count; j++){ AssemblyReference cref = references[j]; if (cref == null) continue; AssemblyNode codeAssembly = cref.Assembly; if (codeAssembly == null || codeAssembly.ContractAssembly != null || codeAssembly.Version == null) continue; if (string.Compare(codeAssembly.Name, contractAssemName, true, CultureInfo.InvariantCulture) != 0) continue; bool sameKey = true; if (publicKey.Length == 0 && codeAssembly.PublicKeyToken == null){ // this is okay: neither has a public key ; }else{ // public keys must match for (int b = 0; sameKey && b < codeAssembly.PublicKeyToken.Length; b++){ if (publicKey[b] != codeAssembly.PublicKeyToken[b]){ sameKey = false; break; } } } if (!sameKey) continue; Version codeAssemblyVersion = codeAssembly.Version; if (codeAssemblyVersion == null) codeAssemblyVersion = new Version(); if (codeAssemblyVersion != contractVersion){ matchesExceptForVersion = codeAssembly; continue; } exactMatch = codeAssembly; break; } if (exactMatch != null) exactMatch.ContractAssembly = contractAssem; else if (matchesExceptForVersion != null) matchesExceptForVersion.ContractAssembly = contractAssem; } module.AssemblyReferences = keepers; }
public virtual MemberList GetNestedNamespacesAndTypes(Identifier name, Scope scope, AssemblyReferenceList assembliesToSearch){ return null; }
public AssemblyReferenceList GetFriendAssemblies() { if(SystemTypes.InternalsVisibleToAttribute == null) return null; AttributeList attributes = this.Attributes; if(attributes == null) return null; int n = attributes.Count; if(n == 0) return null; AssemblyReferenceList result = new AssemblyReferenceList(); for(int i = 0; i < n; i++) { AttributeNode attr = attributes[i]; if(attr == null) continue; MemberBinding mb = attr.Constructor as MemberBinding; if(mb != null) { if(mb.BoundMember == null) continue; if(mb.BoundMember.DeclaringType != SystemTypes.InternalsVisibleToAttribute) continue; } else { Literal lit = attr.Constructor as Literal; if(lit == null) continue; if((lit.Value as TypeNode) != SystemTypes.InternalsVisibleToAttribute) continue; } if(attr.Expressions == null || attr.Expressions.Count < 1) continue; Literal argLit = attr.Expressions[0] as Literal; if(argLit == null) continue; string friendName = argLit.Value as string; if(friendName == null) continue; result.Add(new AssemblyReference(friendName)); } return result; }
protected virtual void GetNestedNamespacesAndTypes(Identifier name, Scope scope, bool constructorMustBeVisible, MemberList list, TrivialHashtable alreadyInList, AssemblyReferenceList assembliesToSearch, bool listAllUnderRootNamespace) { if (name == null || scope == null || this.currentModule == null) return; bool mustBeAttribute = scope is AttributeScope; string nameStr = name.ToString(); int nameLen = nameStr.Length; if (nameLen > 0){ int i = nameStr.LastIndexOf('.'); if (i < 0){ nameLen = 0; nameStr = ""; }else{ nameLen = i; nameStr = nameStr.Substring(0, i); if (this.GetNestedTypesIfNameResolvesToType(nameStr, scope, list, alreadyInList)) return; } } string fullNameStr = null; int fullNameLen = 0; alreadyInList[StandardIds.StructuralTypes.UniqueIdKey] = this; if (assembliesToSearch != null && assembliesToSearch.Count > 0) { for (int i = 0, n = assembliesToSearch == null ? 0 : assembliesToSearch.Count; i < n; i++) { AssemblyReference aRef = assembliesToSearch[i]; if (aRef == null || aRef.Assembly == null) continue; if (fullNameStr != null) this.GetNestedNamespacesAndTypes(aRef.Assembly, constructorMustBeVisible, mustBeAttribute, fullNameStr, fullNameLen, list, alreadyInList, listAllUnderRootNamespace); this.GetNestedNamespacesAndTypes(aRef.Assembly, constructorMustBeVisible, mustBeAttribute, nameStr, nameLen, list, alreadyInList, listAllUnderRootNamespace); } return; } while (scope != null && !(scope is NamespaceScope)) scope = scope.OuterScope; NamespaceScope nsScope = scope as NamespaceScope; if (nsScope != null){ Namespace nSpace = nsScope.AssociatedNamespace; if (nSpace != null && nSpace.FullName != null && nSpace.FullName.Length > 0){ fullNameStr = nSpace.FullName; if (nameLen > 0) fullNameStr += "."+nameStr; fullNameLen = fullNameStr.Length; } } if (fullNameStr != null) this.GetNestedNamespacesAndTypes(this.currentModule, constructorMustBeVisible, mustBeAttribute, fullNameStr, fullNameLen, list, alreadyInList, listAllUnderRootNamespace); this.GetNestedNamespacesAndTypes(this.currentModule, constructorMustBeVisible, mustBeAttribute, nameStr, nameLen, list, alreadyInList, listAllUnderRootNamespace); ModuleReferenceList mRefs = this.currentModule.ModuleReferences; for (int i = 0, n = mRefs == null ? 0 : mRefs.Count; i < n; i++){ ModuleReference mRef = mRefs[i]; if (mRef == null || mRef.Module == null) continue; if (fullNameStr != null) this.GetNestedNamespacesAndTypes(mRef.Module, constructorMustBeVisible, mustBeAttribute, fullNameStr, fullNameLen, list, alreadyInList, listAllUnderRootNamespace); this.GetNestedNamespacesAndTypes(mRef.Module, constructorMustBeVisible, mustBeAttribute, nameStr, nameLen, list, alreadyInList, listAllUnderRootNamespace); } AssemblyReferenceList aRefs = this.currentModule.AssemblyReferences; for (int i = 0, n = aRefs == null ? 0 : aRefs.Count; i < n; i++){ AssemblyReference aRef = aRefs[i]; if (aRef == null || aRef.Assembly == null ) continue; if (fullNameStr != null) this.GetNestedNamespacesAndTypes(aRef.Assembly, constructorMustBeVisible, mustBeAttribute, fullNameStr, fullNameLen, list, alreadyInList, listAllUnderRootNamespace); this.GetNestedNamespacesAndTypes(aRef.Assembly, constructorMustBeVisible, mustBeAttribute, nameStr, nameLen, list, alreadyInList, listAllUnderRootNamespace); } }
public virtual MemberList GetNestedNamespacesAndTypes(Identifier name, Scope scope, AssemblyReferenceList assembliesToSearch){ if (name == null || scope == null || this.currentModule == null) return null; MemberList result = new MemberList(); TrivialHashtable alreadyInList = new TrivialHashtable(); this.GetNestedNamespacesAndTypes(name, scope, scope is AttributeScope, result, alreadyInList, assembliesToSearch, false); return result; }
public virtual TypeNode LookupType(Expression tname, AssemblyReferenceList arefs, out TypeNodeList duplicates){ duplicates = null; Identifier name = tname as Identifier; Identifier nspace = Identifier.Empty; QualifiedIdentifier qual = tname as QualifiedIdentifier; if (qual != null){ name = qual.Identifier; nspace = this.ConvertToIdentifier(qual.Qualifier); } TypeNode result = null; for (int i = 0, n = arefs == null ? 0 : arefs.Count; i < n; i++){ AssemblyReference aref = arefs[i]; if (aref == null) continue; AssemblyNode assem = aref.Assembly; if (assem == null) continue; TypeNode t = assem.GetType(nspace, name); if (t == null) continue; if (result != null){ if (duplicates == null){ duplicates = new TypeNodeList(); duplicates.Add(result); } duplicates.Add(t); continue; } result = t; } return result; }
public override MemberList GetNestedNamespacesAndTypes(Identifier name, Scope scope, AssemblyReferenceList assembliesToSearch){ MemberList result = new MemberList(); ErrorHandler errorHandler = new ErrorHandler(new ErrorNodeList(0)); TrivialHashtable scopeFor = new TrivialHashtable(); TrivialHashtable factoryMap = new TrivialHashtable(); TrivialHashtable ambiguousTypes = new TrivialHashtable(); TrivialHashtable referencedLabels = new TrivialHashtable(); Looker looker = new Looker(null, errorHandler, null, ambiguousTypes, referencedLabels); looker.currentModule = this.currentSymbolTable; return looker.GetNestedNamespacesAndTypes(name, scope, assembliesToSearch); }