Files
2026-08-27 10:56:38 -06:00

146 lines
7.6 KiB
C#

using System.Collections.Generic;
using System.Collections.Immutable;
using Microsoft.Cci;
using Microsoft.CodeAnalysis.Collections;
using Microsoft.CodeAnalysis.PooledObjects;
using Microsoft.CodeAnalysis.Symbols;
using Roslyn.Utilities;
namespace Microsoft.CodeAnalysis.Emit;
internal abstract class SymbolMatcher
{
public abstract ITypeReference? MapReference(ITypeReference reference);
public abstract IDefinition? MapDefinition(IDefinition definition);
public abstract INamespace? MapNamespace(INamespace @namespace);
public ISymbolInternal? MapDefinitionOrNamespace(ISymbolInternal symbol)
{
IReference cciAdapter = symbol.GetCciAdapter();
if (!(cciAdapter is IDefinition definition))
{
return MapNamespace((INamespace)cciAdapter)?.GetInternalSymbol();
}
return MapDefinition(definition)?.GetInternalSymbol();
}
public EmitBaseline MapBaselineToCompilation(EmitBaseline baseline, Compilation targetCompilation, CommonPEModuleBuilder targetModuleBuilder, ImmutableDictionary<ISymbolInternal, ImmutableArray<ISymbolInternal>> mappedSynthesizedMembers, ImmutableDictionary<ISymbolInternal, ImmutableArray<ISymbolInternal>> mappedDeletedMembers)
{
IReadOnlyDictionary<ITypeDefinition, int> typesAdded = MapDefinitions(baseline.TypesAdded);
IReadOnlyDictionary<IEventDefinition, int> eventsAdded = MapDefinitions(baseline.EventsAdded);
IReadOnlyDictionary<IFieldDefinition, int> fieldsAdded = MapDefinitions(baseline.FieldsAdded);
IReadOnlyDictionary<IMethodDefinition, int> methodsAdded = MapDefinitions(baseline.MethodsAdded);
IReadOnlyDictionary<IPropertyDefinition, int> propertiesAdded = MapDefinitions(baseline.PropertiesAdded);
IReadOnlyDictionary<IDefinition, int> generationOrdinals = MapDefinitions(baseline.GenerationOrdinals);
return baseline.With(targetCompilation, targetModuleBuilder, baseline.Ordinal, baseline.EncId, generationOrdinals, typesAdded, eventsAdded, fieldsAdded, methodsAdded, baseline.FirstParamRowMap, propertiesAdded, baseline.EventMapAdded, baseline.PropertyMapAdded, baseline.MethodImplsAdded, baseline.CustomAttributesAdded, baseline.TableEntriesAdded, baseline.BlobStreamLengthAdded, baseline.StringStreamLengthAdded, baseline.UserStringStreamLengthAdded, baseline.GuidStreamLengthAdded, new SynthesizedTypeMaps(MapAnonymousTypes(baseline.SynthesizedTypes.AnonymousTypes), MapAnonymousDelegates(baseline.SynthesizedTypes.AnonymousDelegates), MapAnonymousDelegatesWithIndexedNames(baseline.SynthesizedTypes.AnonymousDelegatesWithIndexedNames)), mappedSynthesizedMembers, mappedDeletedMembers, MapAddedOrChangedMethods(baseline.AddedOrChangedMethods), baseline.DebugInformationProvider, baseline.LocalSignatureProvider);
}
private IReadOnlyDictionary<K, V> MapDefinitions<K, V>(IReadOnlyDictionary<K, V> items) where K : class, IDefinition
{
Dictionary<K, V> dictionary = new Dictionary<K, V>(SymbolEquivalentEqualityComparer.Instance);
foreach (KeyValuePair<K, V> item in items)
{
K val = (K)MapDefinition(item.Key);
if (val != null)
{
dictionary.Add(val, item.Value);
}
}
return dictionary;
}
private IReadOnlyDictionary<int, AddedOrChangedMethodInfo> MapAddedOrChangedMethods(IReadOnlyDictionary<int, AddedOrChangedMethodInfo> addedOrChangedMethods)
{
Dictionary<int, AddedOrChangedMethodInfo> dictionary = new Dictionary<int, AddedOrChangedMethodInfo>();
foreach (KeyValuePair<int, AddedOrChangedMethodInfo> addedOrChangedMethod in addedOrChangedMethods)
{
dictionary.Add(addedOrChangedMethod.Key, addedOrChangedMethod.Value.MapTypes(this));
}
return dictionary;
}
private ImmutableSegmentedDictionary<AnonymousTypeKey, AnonymousTypeValue> MapAnonymousTypes(IReadOnlyDictionary<AnonymousTypeKey, AnonymousTypeValue> anonymousTypeMap)
{
ImmutableSegmentedDictionary<AnonymousTypeKey, AnonymousTypeValue>.Builder builder = ImmutableSegmentedDictionary.CreateBuilder<AnonymousTypeKey, AnonymousTypeValue>();
foreach (KeyValuePair<AnonymousTypeKey, AnonymousTypeValue> item in anonymousTypeMap)
{
KeyValuePairUtil.Deconstruct(item, out var key, out var value);
AnonymousTypeKey key2 = key;
AnonymousTypeValue anonymousTypeValue = value;
ITypeDefinition type = (ITypeDefinition)MapDefinition(anonymousTypeValue.Type);
builder.Add(key2, new AnonymousTypeValue(anonymousTypeValue.Name, anonymousTypeValue.UniqueIndex, type));
}
return builder.ToImmutable();
}
private ImmutableSegmentedDictionary<SynthesizedDelegateKey, SynthesizedDelegateValue> MapAnonymousDelegates(IReadOnlyDictionary<SynthesizedDelegateKey, SynthesizedDelegateValue> anonymousDelegates)
{
ImmutableSegmentedDictionary<SynthesizedDelegateKey, SynthesizedDelegateValue>.Builder builder = ImmutableSegmentedDictionary.CreateBuilder<SynthesizedDelegateKey, SynthesizedDelegateValue>();
foreach (KeyValuePair<SynthesizedDelegateKey, SynthesizedDelegateValue> anonymousDelegate in anonymousDelegates)
{
KeyValuePairUtil.Deconstruct(anonymousDelegate, out var key, out var value);
SynthesizedDelegateKey key2 = key;
SynthesizedDelegateValue synthesizedDelegateValue = value;
ITypeDefinition typeDefinition = (ITypeDefinition)MapDefinition(synthesizedDelegateValue.Delegate);
builder.Add(key2, new SynthesizedDelegateValue(typeDefinition));
}
return builder.ToImmutable();
}
private ImmutableSegmentedDictionary<string, AnonymousTypeValue> MapAnonymousDelegatesWithIndexedNames(IReadOnlyDictionary<string, AnonymousTypeValue> anonymousDelegates)
{
ImmutableSegmentedDictionary<string, AnonymousTypeValue>.Builder builder = ImmutableSegmentedDictionary.CreateBuilder<string, AnonymousTypeValue>();
foreach (KeyValuePair<string, AnonymousTypeValue> anonymousDelegate in anonymousDelegates)
{
KeyValuePairUtil.Deconstruct(anonymousDelegate, out var key, out var value);
string key2 = key;
AnonymousTypeValue anonymousTypeValue = value;
ITypeDefinition type = (ITypeDefinition)MapDefinition(anonymousTypeValue.Type);
builder.Add(key2, new AnonymousTypeValue(anonymousTypeValue.Name, anonymousTypeValue.UniqueIndex, type));
}
return builder.ToImmutable();
}
internal ImmutableDictionary<ISymbolInternal, ImmutableArray<ISymbolInternal>> MapSynthesizedOrDeletedMembers(ImmutableDictionary<ISymbolInternal, ImmutableArray<ISymbolInternal>> previousMembers, ImmutableDictionary<ISymbolInternal, ImmutableArray<ISymbolInternal>> newMembers, bool isDeletedMemberMapping)
{
if (previousMembers.Count == 0)
{
return newMembers;
}
ImmutableDictionary<ISymbolInternal, ImmutableArray<ISymbolInternal>>.Builder builder = ImmutableDictionary.CreateBuilder<ISymbolInternal, ImmutableArray<ISymbolInternal>>();
builder.AddRange(newMembers);
foreach (KeyValuePair<ISymbolInternal, ImmutableArray<ISymbolInternal>> previousMember in previousMembers)
{
KeyValuePairUtil.Deconstruct(previousMember, out var key, out var value);
ISymbolInternal symbolInternal = key;
ImmutableArray<ISymbolInternal> value2 = value;
ISymbolInternal symbolInternal2 = MapDefinitionOrNamespace(symbolInternal);
if (symbolInternal2 == null)
{
builder.Add(symbolInternal, value2);
continue;
}
if (!newMembers.TryGetValue(symbolInternal2, out ImmutableArray<ISymbolInternal> value3))
{
builder.Add(symbolInternal2, value2);
continue;
}
ArrayBuilder<ISymbolInternal> instance = ArrayBuilder<ISymbolInternal>.GetInstance();
instance.AddRange(value3);
ImmutableArray<ISymbolInternal>.Enumerator enumerator2 = value2.GetEnumerator();
while (enumerator2.MoveNext())
{
ISymbolInternal current = enumerator2.Current;
if (MapDefinitionOrNamespace(current) == null)
{
instance.Add(current);
}
}
builder[symbolInternal2] = instance.ToImmutableAndFree();
}
return builder.ToImmutable();
}
}